增加网关跨域处理
This commit is contained in:
3
Dockerfile
Normal file
3
Dockerfile
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
FROM openjdk:8-jdk-alpine
|
||||||
|
COPY target/sczx-gateway.jar app.jar
|
||||||
|
ENTRYPOINT ["java", "-jar", "-Xms256m", "-Xmx512m", "app.jar"]
|
||||||
77
Jenkinsfile
vendored
Normal file
77
Jenkinsfile
vendored
Normal file
@ -0,0 +1,77 @@
|
|||||||
|
pipeline {
|
||||||
|
agent any
|
||||||
|
tools {
|
||||||
|
maven 'M3'
|
||||||
|
}
|
||||||
|
environment {
|
||||||
|
APP_NAME = "sczx-gateway"
|
||||||
|
DOCKER_IMAGE = "${APP_NAME}:latest"
|
||||||
|
CONTAINER_NAME = "${APP_NAME}-container"
|
||||||
|
}
|
||||||
|
|
||||||
|
stages {
|
||||||
|
stage('Checkout') {
|
||||||
|
steps {
|
||||||
|
echo "📦 正在拉取代码..."
|
||||||
|
git branch: 'main', url: '你的 Git 仓库地址'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
stage('Build with Maven') {
|
||||||
|
steps {
|
||||||
|
echo "🛠️ 正在使用 Maven 构建..."
|
||||||
|
sh 'mvn clean package -s settings.xml'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
stage('Check Jar File') {
|
||||||
|
steps {
|
||||||
|
sh 'ls -la target/' // 确保 jar 文件存在
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
stage('Build Docker Image') {
|
||||||
|
steps {
|
||||||
|
echo "🐋 正在构建 Docker 镜像..."
|
||||||
|
sh """
|
||||||
|
docker build -t \${DOCKER_IMAGE} .
|
||||||
|
"""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
stage('Stop Old Container') {
|
||||||
|
steps {
|
||||||
|
echo "🛑 正在停止旧容器..."
|
||||||
|
sh '''
|
||||||
|
if [ "$(docker ps -f 'name=sczx-gateway-container' --format '{{.Status}}')" ]; then
|
||||||
|
docker stop sczx-gateway-container
|
||||||
|
docker rm sczx-gateway-container
|
||||||
|
fi
|
||||||
|
'''
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
stage('Run New Container') {
|
||||||
|
steps {
|
||||||
|
echo "🟢 正在运行新容器..."
|
||||||
|
sh """
|
||||||
|
docker run -d \
|
||||||
|
--name \${CONTAINER_NAME} \
|
||||||
|
-p 8089:8089 \
|
||||||
|
-e JAVA_OPTS="-Xms256m -Xmx512m -Duser.timezone=Asia/Shanghai" \
|
||||||
|
--restart always \
|
||||||
|
\${DOCKER_IMAGE}
|
||||||
|
"""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
post {
|
||||||
|
success {
|
||||||
|
echo "🎉 构建成功!网关已部署到 Docker 容器中。"
|
||||||
|
}
|
||||||
|
failure {
|
||||||
|
echo "❌ 构建失败,请检查日志!"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
156
pom.xml
Normal file
156
pom.xml
Normal file
@ -0,0 +1,156 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||||
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||||
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
||||||
|
<groupId>com.sczx</groupId>
|
||||||
|
<artifactId>sczx-gateway</artifactId>
|
||||||
|
<version>1.0.0</version>
|
||||||
|
<packaging>jar</packaging>
|
||||||
|
|
||||||
|
<name>sczx-gateway</name>
|
||||||
|
<description>统一 API 网关服务</description>
|
||||||
|
|
||||||
|
<properties>
|
||||||
|
<java.version>1.8</java.version>
|
||||||
|
<spring-boot.version>2.3.12.RELEASE</spring-boot.version>
|
||||||
|
<spring-cloud.version>Hoxton.SR12</spring-cloud.version>
|
||||||
|
<spring-cloud-alibaba.version>2.2.9.RELEASE</spring-cloud-alibaba.version>
|
||||||
|
</properties>
|
||||||
|
|
||||||
|
<!-- Parent -->
|
||||||
|
<parent>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-parent</artifactId>
|
||||||
|
<version>2.3.12.RELEASE</version>
|
||||||
|
<relativePath/>
|
||||||
|
</parent>
|
||||||
|
|
||||||
|
<!-- Dependency Management -->
|
||||||
|
<dependencyManagement>
|
||||||
|
<dependencies>
|
||||||
|
<!-- Spring Cloud Greenwich.SR6 -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.cloud</groupId>
|
||||||
|
<artifactId>spring-cloud-dependencies</artifactId>
|
||||||
|
<version>${spring-cloud.version}</version>
|
||||||
|
<type>pom</type>
|
||||||
|
<scope>import</scope>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<!-- Spring Cloud Alibaba -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.alibaba.cloud</groupId>
|
||||||
|
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
|
||||||
|
<version>${spring-cloud-alibaba.version}</version>
|
||||||
|
<type>pom</type>
|
||||||
|
<scope>import</scope>
|
||||||
|
</dependency>
|
||||||
|
</dependencies>
|
||||||
|
</dependencyManagement>
|
||||||
|
|
||||||
|
<!-- Dependencies -->
|
||||||
|
<dependencies>
|
||||||
|
<!-- Spring WebFlux -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-webflux</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<!-- Spring Cloud Gateway -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.cloud</groupId>
|
||||||
|
<artifactId>spring-cloud-starter-gateway</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<!-- Nacos Discovery -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.alibaba.cloud</groupId>
|
||||||
|
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<!-- Actuator 监控 -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<!-- Redis 限流支持 -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-data-redis-reactive</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
|
||||||
|
<!-- Lombok -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.projectlombok</groupId>
|
||||||
|
<artifactId>lombok</artifactId>
|
||||||
|
<version>1.18.24</version>
|
||||||
|
<scope>provided</scope>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<!-- Swagger 文档 -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springdoc</groupId>
|
||||||
|
<artifactId>springdoc-openapi-ui</artifactId>
|
||||||
|
<version>1.6.14</version>
|
||||||
|
</dependency>
|
||||||
|
</dependencies>
|
||||||
|
|
||||||
|
<!-- Build Configuration -->
|
||||||
|
<build>
|
||||||
|
<finalName>sczx-gateway</finalName>
|
||||||
|
<resources>
|
||||||
|
<resource>
|
||||||
|
<directory>src/main/resources</directory>
|
||||||
|
<includes>
|
||||||
|
<include>*.yml</include>
|
||||||
|
</includes>
|
||||||
|
<filtering>true</filtering>
|
||||||
|
</resource>
|
||||||
|
<resource>
|
||||||
|
<directory>src/main/resources</directory>
|
||||||
|
<excludes>
|
||||||
|
<exclude>*.yml</exclude>
|
||||||
|
</excludes>
|
||||||
|
</resource>
|
||||||
|
</resources>
|
||||||
|
<plugins>
|
||||||
|
<!-- Compiler Plugin -->
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.apache.maven.plugins</groupId>
|
||||||
|
<artifactId>maven-compiler-plugin</artifactId>
|
||||||
|
<configuration>
|
||||||
|
<source>${java.version}</source>
|
||||||
|
<target>${java.version}</target>
|
||||||
|
</configuration>
|
||||||
|
</plugin>
|
||||||
|
|
||||||
|
<!-- Spring Boot Maven Plugin -->
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-maven-plugin</artifactId>
|
||||||
|
<executions>
|
||||||
|
<execution>
|
||||||
|
<goals>
|
||||||
|
<goal>repackage</goal>
|
||||||
|
</goals>
|
||||||
|
</execution>
|
||||||
|
</executions>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.apache.maven.plugins</groupId>
|
||||||
|
<artifactId>maven-source-plugin</artifactId>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.apache.maven.plugins</groupId>
|
||||||
|
<artifactId>maven-deploy-plugin</artifactId>
|
||||||
|
<configuration>
|
||||||
|
<skip>true</skip>
|
||||||
|
</configuration>
|
||||||
|
</plugin>
|
||||||
|
</plugins>
|
||||||
|
</build>
|
||||||
|
</project>
|
||||||
12
settings.xml
Normal file
12
settings.xml
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
<settings xmlns="http://maven.apache.org/SETTINGS/1.0.0"
|
||||||
|
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://maven.apache.org/SETTINGS/1.0.0 https://maven.apache.org/xsd/settings-1.0.0.xsd">
|
||||||
|
<mirrors>
|
||||||
|
<mirror>
|
||||||
|
<id>aliyun-maven</id>
|
||||||
|
<mirrorOf>*</mirrorOf>
|
||||||
|
<name>Aliyun Maven</name>
|
||||||
|
<url>https://maven.aliyun.com/repository/public</url>
|
||||||
|
</mirror>
|
||||||
|
</mirrors>
|
||||||
|
</settings>
|
||||||
11
src/main/java/com/sczx/gateway/GatewayApplication.java
Normal file
11
src/main/java/com/sczx/gateway/GatewayApplication.java
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
package com.sczx.gateway;
|
||||||
|
|
||||||
|
import org.springframework.boot.SpringApplication;
|
||||||
|
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||||
|
|
||||||
|
@SpringBootApplication
|
||||||
|
public class GatewayApplication {
|
||||||
|
public static void main(String[] args) {
|
||||||
|
SpringApplication.run(GatewayApplication.class, args);
|
||||||
|
}
|
||||||
|
}
|
||||||
35
src/main/java/com/sczx/gateway/filter/AuthGlobalFilter.java
Normal file
35
src/main/java/com/sczx/gateway/filter/AuthGlobalFilter.java
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
package com.sczx.gateway.filter;
|
||||||
|
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.cloud.gateway.filter.GlobalFilter;
|
||||||
|
import org.springframework.cloud.gateway.filter.GatewayFilterChain;
|
||||||
|
import org.springframework.core.Ordered;
|
||||||
|
import org.springframework.http.HttpStatus;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
import org.springframework.web.server.ServerWebExchange;
|
||||||
|
import reactor.core.publisher.Mono;
|
||||||
|
|
||||||
|
@Component
|
||||||
|
@Slf4j
|
||||||
|
public class AuthGlobalFilter implements GlobalFilter, Ordered {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
|
||||||
|
String path = exchange.getRequest().getPath().value();
|
||||||
|
log.info("🌐 请求路径: {}", path);
|
||||||
|
|
||||||
|
// 示例:拦截所有请求,校验 token
|
||||||
|
// String token = exchange.getRequest().getHeaders().getFirst("Authorization");
|
||||||
|
// if (token == null || !token.startsWith("Bearer ")) {
|
||||||
|
// exchange.getResponse().setStatusCode(HttpStatus.UNAUTHORIZED);
|
||||||
|
// return exchange.getResponse().setComplete();
|
||||||
|
// }
|
||||||
|
|
||||||
|
return chain.filter(exchange);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getOrder() {
|
||||||
|
return 0; // 执行顺序
|
||||||
|
}
|
||||||
|
}
|
||||||
34
src/main/java/com/sczx/gateway/filter/CorsGlobalFilter.java
Normal file
34
src/main/java/com/sczx/gateway/filter/CorsGlobalFilter.java
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
package com.sczx.gateway.filter;
|
||||||
|
|
||||||
|
import org.springframework.cloud.gateway.filter.GatewayFilterChain;
|
||||||
|
import org.springframework.cloud.gateway.filter.GlobalFilter;
|
||||||
|
import org.springframework.context.annotation.Configuration;
|
||||||
|
import org.springframework.http.HttpHeaders;
|
||||||
|
import org.springframework.http.HttpStatus;
|
||||||
|
import org.springframework.web.server.ServerWebExchange;
|
||||||
|
import reactor.core.publisher.Mono;
|
||||||
|
|
||||||
|
@Configuration
|
||||||
|
public class CorsGlobalFilter implements GlobalFilter {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
|
||||||
|
HttpHeaders headers = exchange.getRequest().getHeaders();
|
||||||
|
// 判断是否为跨域请求
|
||||||
|
if (headers.containsKey("Origin")) {
|
||||||
|
HttpHeaders responseHeaders = exchange.getResponse().getHeaders();
|
||||||
|
responseHeaders.add("Access-Control-Allow-Origin", "*");
|
||||||
|
responseHeaders.add("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
|
||||||
|
responseHeaders.add("Access-Control-Allow-Headers", "*");
|
||||||
|
responseHeaders.add("Access-Control-Allow-Credentials", "true");
|
||||||
|
responseHeaders.add("Access-Control-Max-Age", "3600");
|
||||||
|
responseHeaders.add("Access-Control-Expose-Headers", "*");
|
||||||
|
}
|
||||||
|
// 如果是 OPTIONS 预检请求,直接返回 200
|
||||||
|
if ("OPTIONS".equalsIgnoreCase(exchange.getRequest().getMethodValue())) {
|
||||||
|
exchange.getResponse().setStatusCode(HttpStatus.OK);
|
||||||
|
return exchange.getResponse().setComplete();
|
||||||
|
}
|
||||||
|
return chain.filter(exchange);
|
||||||
|
}
|
||||||
|
}
|
||||||
36
src/main/resources/application.yml
Normal file
36
src/main/resources/application.yml
Normal file
@ -0,0 +1,36 @@
|
|||||||
|
server:
|
||||||
|
port: 8089
|
||||||
|
shutdown: graceful # 启用优雅停机
|
||||||
|
|
||||||
|
spring:
|
||||||
|
application:
|
||||||
|
name: sczx-gateway
|
||||||
|
cloud:
|
||||||
|
gateway:
|
||||||
|
discovery:
|
||||||
|
locator:
|
||||||
|
enabled: true # 开启从注册中心动态获取路由
|
||||||
|
lower-case-service-id: true # 服务名转小写
|
||||||
|
routes:
|
||||||
|
- id: user-service
|
||||||
|
uri: lb://sczx-app
|
||||||
|
predicates:
|
||||||
|
- Path=/zc/app/**
|
||||||
|
filters:
|
||||||
|
- StripPrefix=1
|
||||||
|
nacos:
|
||||||
|
discovery:
|
||||||
|
server-addr: 115.190.8.52:8848 # Nacos 地址
|
||||||
|
group: DEFAULT_GROUP
|
||||||
|
metadata:
|
||||||
|
version: 1.0.0
|
||||||
|
env: dev
|
||||||
|
|
||||||
|
management:
|
||||||
|
endpoints:
|
||||||
|
web:
|
||||||
|
exposure:
|
||||||
|
include: "*"
|
||||||
|
endpoint:
|
||||||
|
health:
|
||||||
|
show-details: always
|
||||||
53
src/main/resources/logback.xml
Normal file
53
src/main/resources/logback.xml
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
|
||||||
|
<configuration>
|
||||||
|
<!--%d表示日期,%X表示输出所有,:null表示为空时输出null,%level表示日志级别 %thread表示线程名字 %c表示类名 %L表示行号 %n表示换行符-->
|
||||||
|
<property name="PATTERN"
|
||||||
|
value="%-12(%d{yyyy-MM-dd HH:mm:ss.SSS}) [%X{EagleEye-TraceID}%X{EagleEye-TraceID-Copy}] %level [%thread] %c[%L] %X{requestId} %msg%n"/>
|
||||||
|
<property name="LOG_FILE_PATH" value="./logs"/>
|
||||||
|
<appender name="STDOUT"
|
||||||
|
class="ch.qos.logback.core.ConsoleAppender">
|
||||||
|
<encoder>
|
||||||
|
<pattern>${PATTERN}</pattern>
|
||||||
|
</encoder>
|
||||||
|
</appender>
|
||||||
|
|
||||||
|
<appender name="INFO_FILE_APPENDER" class="ch.qos.logback.core.rolling.RollingFileAppender">
|
||||||
|
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
|
||||||
|
<fileNamePattern>${LOG_FILE_PATH}/${hostname}/info.%d{yyyy-MM-dd}.log</fileNamePattern>
|
||||||
|
<MaxHistory>31</MaxHistory>
|
||||||
|
</rollingPolicy>
|
||||||
|
<encoder class="ch.qos.logback.core.encoder.LayoutWrappingEncoder">
|
||||||
|
<layout class="ch.qos.logback.classic.PatternLayout">
|
||||||
|
<pattern>${PATTERN}</pattern>
|
||||||
|
</layout>
|
||||||
|
</encoder>
|
||||||
|
<filter class="ch.qos.logback.classic.filter.LevelFilter">
|
||||||
|
<level>WARN</level>
|
||||||
|
<onMatch>DENY</onMatch>
|
||||||
|
<onMismatch>NEUTRAL</onMismatch>
|
||||||
|
</filter>
|
||||||
|
<filter class="ch.qos.logback.classic.filter.LevelFilter">
|
||||||
|
<level>ERROR</level>
|
||||||
|
<onMatch>DENY</onMatch>
|
||||||
|
<onMismatch>NEUTRAL</onMismatch>
|
||||||
|
</filter>
|
||||||
|
</appender>
|
||||||
|
|
||||||
|
<appender name="WARN_FILE_APPENDER" class="ch.qos.logback.core.FileAppender">
|
||||||
|
<filter class="ch.qos.logback.classic.filter.ThresholdFilter">
|
||||||
|
<level>WARN</level>
|
||||||
|
</filter>
|
||||||
|
<file>${LOG_FILE_PATH}/${hostname}/warn.log</file>
|
||||||
|
<append>true</append>
|
||||||
|
<encoder>
|
||||||
|
<pattern>${PATTERN}</pattern>
|
||||||
|
</encoder>
|
||||||
|
</appender>
|
||||||
|
|
||||||
|
<root level="info">
|
||||||
|
<appender-ref ref="INFO_FILE_APPENDER"/>
|
||||||
|
<appender-ref ref="WARN_FILE_APPENDER"/>
|
||||||
|
<appender-ref ref="STDOUT"/>
|
||||||
|
</root>
|
||||||
|
</configuration>
|
||||||
Reference in New Issue
Block a user