# springCloud **Repository Path**: caicongyang/springcloud ## Basic Information - **Project Name**: springCloud - **Description**: springCloud test cese - **Primary Language**: Java - **License**: Apache-2.0 - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 9 - **Forks**: 14 - **Created**: 2017-05-01 - **Last Updated**: 2025-05-12 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # springCloud #### 介绍 个人springCloud 测试项目 #### 主要实现功能: 基础git branch 的分支管理,实现多版本一套环境共同开发 ## 架构图 ```mermaid graph TD subgraph "开发者工作区" Dev1["开发者 1"] Dev2["开发者 2"] Dev3["开发者 3"] end subgraph "Git 仓库" GitRepo["Configuration Repo
springCloudConfigRepo.git"] Master["Master Branch"] DevBranch["Dev Branch"] TestBranch["Test Branch"] ProdBranch["Production Branch"] GitRepo --> Master GitRepo --> DevBranch GitRepo --> TestBranch GitRepo --> ProdBranch Dev1 --> GitRepo Dev2 --> GitRepo Dev3 --> GitRepo end subgraph "配置服务器" ConfigServer["Config Server
Port: 1234"] ConfigServer --> GitRepo end subgraph "服务注册与发现" Eureka["Eureka Server
Port: 9999"] subgraph "元数据管理" AppMetadata["服务元数据
branch: xxx"] end AppMetadata --> Eureka end subgraph "网关服务" Gateway["API Gateway
Port: 8888"] BranchFilter["GitBranchFilter
根据规则选择分支"] BranchRule["GitBranchRule
负载均衡规则"] Gateway --> BranchFilter BranchFilter --> BranchRule Gateway --> Eureka end subgraph "微服务" CommonRunner["CommonApplicationRunner
注册Git分支元数据"] OrderService["Order Service
Port: 8081
Profile: dev"] AppService["App Service
Profile: dev"] CommonRunner --> OrderService CommonRunner --> AppService OrderService --> ConfigServer OrderService --> Eureka AppService --> ConfigServer AppService --> Eureka end Client["客户端"] --> |"请求带branch标识"|Gateway BranchFilter --> |"选择对应分支的实例"|OrderService BranchFilter --> |"选择对应分支的实例"|AppService style BranchFilter fill:#f96,stroke:#333,stroke-width:2px style BranchRule fill:#f96,stroke:#333,stroke-width:2px style CommonRunner fill:#f96,stroke:#333,stroke-width:2px ``` ## 多分支全链路追踪机制 (核心功能) 这是本项目的核心创新点,通过以下组件实现: ### 服务分支元数据注册 (`CommonApplicationRunner.java`) ```java @Component public class CommonApplicationRunner implements ApplicationRunner { @Autowired ApplicationInfoManager manager; @Autowired private GitProperties gitProperties; @Override public void run(ApplicationArguments args) throws Exception { Map branch = new HashMap<>(); branch.put("branch", gitProperties.getBranch()); manager.registerAppMetadata(branch); } } ``` - 每个微服务启动时,通过 `CommonApplicationRunner` 获取当前 Git 分支信息 - 将分支信息作为元数据注册到 Eureka 服务注册中心 - 这样每个服务实例在 Eureka 中都会带有所属的 Git 分支标识 ### 网关层分支路由过滤器 (`GitBranchFilter.java`) ```java @Component public class GitBranchFilter extends LoadBalancerClientFilter { @Autowired DiscoveryClient client; @Override protected ServiceInstance choose(ServerWebExchange exchange) { ServerHttpRequest request = exchange.getRequest(); // 可以从 HTTP 请求头中获取分支信息 // 也可以基于用户 IP 地址动态映射到特定分支 String ipAddress = IPUtil.getIpAddress(request); String branch = "master"; // 默认分支,可根据规则动态确定 URI uri = exchange.getAttribute(GATEWAY_REQUEST_URL_ATTR); String host = uri.getHost(); List instances = client.getInstances(host); // 筛选出指定分支的服务实例 List branchList = instances.stream() .filter(a -> a.getMetadata().get("branch") .equalsIgnoreCase(branch)) .collect(Collectors.toList()); if (CollectionUtils.isEmpty(branchList)) { //默认 master 分支 branchList = instances.stream() .filter(a -> a.getMetadata().get("branch") .equalsIgnoreCase("master")) .collect(Collectors.toList()); } // 将分支信息传递给下游服务 exchange.mutate().request(request.mutate().header("branch", branch).build()).build(); return branchList.get(0); } } ``` - 网关接收到请求后,通过 `GitBranchFilter` 获取请求中的分支信息 - 根据分支信息从服务注册中心筛选出对应分支的服务实例 - 将分支信息添加到请求头中,传递给下游服务,实现全链路分支追踪 ### 负载均衡规则 (`GitBranchRule.java`) ```java public class GitBranchRule extends ZoneAvoidanceRule { @Override public Server choose(Object key) { ILoadBalancer lb = this.getLoadBalancer(); List allServers = filterServers(lb.getAllServers()); Optional server = this.getPredicate().chooseRoundRobinAfterFiltering(allServers, key); return server.isPresent() ? (Server) server.get() : null; } private List filterServers(List serverList) { String branch = "master"; // 可从上下文获取 if (StringUtils.isNotBlank(branch)) { List list = new ArrayList<>(); for (Server server : serverList) { if (((DiscoveryEnabledServer) server).getInstanceInfo() .getMetadata().get("branch").equalsIgnoreCase(branch)) { list.add(server); } } return list; } else { return serverList; // 默认返回所有服务 } } } ``` - 自定义负载均衡规则,确保请求只路由到相同分支的服务实例 - 从所有可用服务中筛选出对应分支的服务进行负载均衡 #### 参考: https://mp.weixin.qq.com/s/AViqUPlTyxcb8okDiDXHrQ https://jishuin.proginn.com/p/763bfbd60aad