zoukankan      html  css  js  c++  java
  • 【微服务】仿微服务式集成组件

    一、背景及设计思路

    现行多系统间http请求接口方式交互,于是就会产生如下问题:① url或uri需要用数据库或枚举存储,需要查库或者拼接url; ② 系统服务地址都需要在项目中配置定义,没有统一管理,修改添加代码成本大。

    以我们项目为例,url地址作为param在数据库中存储,不同环境url的服务地址各不相同,这样给数据库脚本维护及上线带来潜在风险。同样,在修改uri或服务器迁移(如果域名解析的话,就没有此问题),就需要对个环境做param清洗,增加开发工作量。

    在尽量对原有项目较少改动的前提下,设计思路如下:

    1、针对各项目散落的系统服务地址问题,方法就是将URL地址从系统抽离。

          将原先URL地址拆分为“服务地址+uri”,按照各profile地址,将服务器地址同一管理起来,作为父pom供各系统继承。此处还将各环境公用的环境配置信息都抽到父pom中,诸如:redis地址、zk地址、kafka地址等。

    2、针对uri问题    分两步解决,① 存储:之所以选择枚举而不是数据库存储,主要是考虑到uri修改频率较低。另外,如果用数据库存储,最好还是同缓存共同管理uri,以此减少与数据库交互的次数。

          ② url拼接:首先根据各系统提供的api接口,分类将uri存到对应枚举。系统启动时,将各请求url对应的code值初始化到内存,并暴露出接口供系统调用。

      将上述代码实现封装到 client.jar 中,作为集成组件,系统调用对应接口即可。

    二、实现

    1、父类pom文件,很简单没啥说的,可以看到其中除了地址还定义了 redis地址,kafka开关,秘钥等信息。

    <?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.vegHunter</groupId>
        <artifactId>common-parent</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <packaging>pom</packaging>
        <name>System Starter Parent</name>
        <description>Parent pom providing dependency and plugin management for applications of any system</description>
        <properties>
            <java.version>1.7</java.version>
            <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
            <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
            <maven.compiler.source>${java.version}</maven.compiler.source>
            <maven.compiler.target>${java.version}</maven.compiler.target>
    
            <!-- micro service name -->
            <micro.service.name>mservice</micro.service.name>
    
            <kafka.used.flag>closed</kafka.used.flag>
    
            <!-- The deployment address of all micro services -->
            <!-- 默认地址,若又不一样,在profile里重写覆盖即可 -->
            <server.url.serviceA>http://a.vegHunter.com</server.url.serviceA>
            <server.url.serviceB>http://b.vegHunter.com</server.url.serviceB>
            <server.url.serviceC>http://c.vegHunter.com</server.url.serviceC>
    
            <server.local.url.serviceA></server.local.url.serviceA>
            <server.local.url.serviceB></server.local.url.serviceB>
            <server.local.url.serviceC></server.local.url.serviceC>
        </properties>
        <profiles>
            <!-- 开发 -->
            <profile>
                <id>dev</id>
                <properties>
                    <deploy.profile>dev</deploy.profile>
                    <kafka.used.flag>closed</kafka.used.flag>
                    <!-- jedis -->
                    <JedisPool.host>10.10.10.100</JedisPool.host>
                    <JedisPool.port>6381</JedisPool.port>
                    <JedisPool.password>redis6381</JedisPool.password>
                    <JedisPool.database>1</JedisPool.database>
                    <!-- The deployment address of all micro services -->
                    <!-- 没有定义就是用默认的 -->
    
                    <!-- 加签秘钥-->
                    <params.http.securityCode>devsalt1</params.http.securityCode>
                </properties>
            </profile>
            <!-- 生产 -->
            <profile>
                <id>pro</id>
                <properties>
                    <deploy.profile>pro</deploy.profile>
                    <kafka.used.flag>closed</kafka.used.flag>
                    <!-- jedis -->
                    <JedisPool.host>10.10.10.101</JedisPool.host>
                    <JedisPool.port>6381</JedisPool.port>
                    <JedisPool.password>redis6381</JedisPool.password>
                    <JedisPool.database>2</JedisPool.database>
    
                    <!-- The deployment address of all micro services -->
                    <server.url.serviceA>http://pro-a.veghunter.com</server.url.serviceA>
                    <server.url.serviceB>http://pro-b.vegHunter.com</server.url.serviceB>
                    <server.url.serviceC>http://pro-c.vegHunter.com</server.url.serviceC>
    
                    <!-- The deployment local address of all micro services -->
                    <server.local.url.serviceA>http://pro-local-a.vegHunter.com</server.local.url.serviceA>
                    <server.local.url.serviceB>http://pro-local-b.vegHunter.com</server.local.url.serviceB>
                    <server.local.url.serviceC>https://pro-local-c.vegHunter.com</server.local.url.serviceC>
    
                    <params.http.securityCode>prosalt1</params.http.securityCode>
                </properties>
            </profile>
        </profiles>
        <build>
            <plugins>
                <plugin>
                    <artifactId>maven-compiler-plugin</artifactId>
                    <version>3.1</version>
                    <configuration>
                        <source>${java.version}</source>
                        <target>${java.version}</target>
                        <encoding>${project.build.sourceEncoding}</encoding>
                    </configuration>
                </plugin>
                <plugin>
                    <groupId>org.apache.maven.plugins</groupId>
                    <artifactId>maven-surefire-plugin</artifactId>
                    <version>2.5</version>
                </plugin>
                <plugin>
                    <artifactId>maven-resources-plugin</artifactId>
                    <version>2.6</version>
                    <configuration>
                        <encoding>UTF-8</encoding>
                    </configuration>
                </plugin>
                <plugin>
                    <groupId>org.codehaus.mojo</groupId>
                    <artifactId>build-helper-maven-plugin</artifactId>
                    <version>3.0.0</version>
                    <executions>
                        <execution>
                            <id>timestamp-property</id>
                            <goals>
                                <goal>timestamp-property</goal>
                            </goals>
                            <configuration>
                                <name>build.time</name>
                                <pattern>yyyyMMdd-HHmm</pattern>
                                <locale>en</locale>
                                <timeZone>Asia/Shanghai</timeZone>
                            </configuration>
                        </execution>
                    </executions>
                </plugin>
                <plugin>
                    <groupId>org.apache.tomcat.maven</groupId>
                    <artifactId>tomcat7-maven-plugin</artifactId>
                    <version>2.1</version>
                    <configuration>
                        <contextReloadable>false</contextReloadable>
                        <uriEncoding>UTF-8</uriEncoding>
                        <path>/</path>
                    </configuration>
                </plugin>
            </plugins>
        </build>
        <dependencyManagement>
            <dependencies>
                ... 各种依赖
            </dependencies>
        </dependencyManagement>
    </project>
    View Code

    2、项目依赖 父pom文件

      同时定义一个json文件,用于初始化各服务地址。

    [
      {
        "name": "A",
        "serverUrl": "${server.url.serviceA}",
        "localServerUrl": "${server.local.url.serviceA}"
      },
      {
        "name": "B",
        "serverUrl": "${server.url.serviceB}",
        "localServerUrl": "${server.local.url.serviceB}"
      },
      {
        "name": "C",
        "serverUrl": "${server.url.serviceC}",
        "localServerUrl": "${server.local.url.serviceC}"
      }
    ]

    3、client.jar 中拼接url并提供接口

    接下来写一些伪代码,主要看思路

    定义所有服务的枚举

    public enum MicroServiceEnum {
        A("A","A系统"),
        B("B","B系统"),
        C("C","C系统")
    }

    定义各服务对应的uri枚举

    public enum AMicroServiceEnum {
        AURI-1("/query/users","检索用户列表"),
        BURI-2("/editUser","修改用户"),
        CURL-3("/addUser","添加用户")
    }

    初始化类(系统启动时,初始化地址及uri信息到内存)

    public class MicroServiceInitializer {
    
         private MicroServiceInitializer {super();} 
    
         public static synchronized Map<String, MicroServiceInfo> init() {
               //1.遍历系统定义的json格式,将各属性赋值 
               //2.找到对应服务,遍历服务对应的uri
               //3.将上述两步组成serviceMap,key值为服务code,value为实体(包含服务地址,uri的map格式)
               //4.将封装好的serviceMap放到内存
        }  
    }    

    拼接URL,提供接口

    public class AMicroClientService {
            
        private final MicroServiceEnum enun = MicroServiceEnum.A;
    
        public static String getAUri1() {
           //1. 根据enun找到对应的服务对象
           //2. 根据AUri1对应的code,从服务对象中的map找到服务对应的uri
           //3. 拼接返回
        }
        public static String getAUri2(String code) {
        //同上
        }
        public static String getAUri3(String code) {
        //同上  
        }
    }

    3、后记

    至此,一个仿微服务的组件就基本搭出框架了。其实,本质上这个并不是微服务,系统间请求仍由HTTP完成,只不过是请求地址由Client封装提供,以此管理多而复杂的请求地址。

    目前比较主流的微服务框架有:Spring Cloud, Dubbo。

    Dubbo 本人已经有写了一个简单的例子,具体原理还没有分析。

    Spring Cloud 后续接触了再做总结。

  • 相关阅读:
    25.C++- 泛型编程之函数模板(详解)
    Windows10 + Visual Studio 2017 + CMake +OpenCV编译、开发环境配置及测试
    终于解决了python 3.x import cv2 “ImportError: DLL load failed: 找不到指定的模块” 及“pycharm关于cv2没有代码提示”的问题
    Python的开源人脸识别库:离线识别率高达99.38%(附源码)
    python获取公网ip的几种方式
    Chrome与chromedriver.exe的版本对应
    Google Gson用法
    idea 报错javax/xml/bind/DatatypeConverter
    org.slf4j:slf4j-api:添加日志管理
    基本使用——OkHttp3详细使用教程
  • 原文地址:https://www.cnblogs.com/liuxs13/p/9298291.html
Copyright © 2011-2022 走看看