自研服务治理框架----服务注册

Zookeeper客户端Curator

Curator是Netflix公司开源的一套zookeeper客户端框架,Curator无疑是Zookeeper客户端中的瑞士军刀,解决了很多Zookeeper客户端非常底层的细节开发工作,包括连接重连、反复注册Watcher和NodeExistsException异常等等。

Curator包含了几个包:

  • curator-framework:对zookeeper的底层api的一些封装
  • curator-client:提供一些客户端的操作,例如重试策略等
  • curator-recipes:封装了一些高级特性,如:Cache事件监听、选举、分布式锁、分布式计数器、分布式Barrier等

Mavn依赖

        <dependency>
            <groupId>org.apache.curator</groupId>
            <artifactId>curator-framework</artifactId>
            <version>2.12.0</version>
        </dependency>
        <dependency>
            <groupId>org.apache.curator</groupId>
            <artifactId>curator-recipes</artifactId>
            <version>2.12.0</version>
        </dependency>

注册接口

    @Override  
    public void register(String service, String version, String address) {  
        if(zkClient.getState() == CuratorFrameworkState.LATENT){  
            zkClient.start();  
        }  
        if(StringUtils.isEmpty(version)){  
            version="1.0.0";  
        }  
        //临时节点  
        try {  
            zkClient.create()  
                .creatingParentsIfNeeded()  
                .withMode(CreateMode.EPHEMERAL)  
                .forPath("/"+service+"/"+version+"/"+address);  
        } catch (UnsupportedEncodingException e) {  
            logger.error("register service address to zookeeper exception:{}",e);  
            throw new ThriftException("register service address to zookeeper exception: address UnsupportedEncodingException", e);  
        } catch (Exception e) {  
            logger.error("register service address to zookeeper exception:{}",e);  
            throw new ThriftException("register service address to zookeeper exception:{}", e);  
        }  
    }  

服务注册

public class ThriftServiceServerFactory implements InitializingBean {  
    // 服务注册本机端口  
    private Integer port = 8299;  
    // 优先级  
    private Integer weight = 1;// default  
    // 服务实现类  
    private Object service;// serice实现类  
    //服务版本号  
    private String version;  
    // 解析本机IP  
    private ThriftServerIpResolve thriftServerIpResolve;  
    //服务注册  
    private ThriftServerAddressRegister thriftServerAddressRegister;  
  
    private ServerThread serverThread;  
      
    public void setPort(Integer port) {  
        this.port = port;  
    }  
  
    public void setWeight(Integer weight) {  
        this.weight = weight;  
    }  
  
    public void setService(Object service) {  
        this.service = service;  
    }  
  
    public void setVersion(String version) {  
        this.version = version;  
    }  
  
    public void setThriftServerIpResolve(ThriftServerIpResolve thriftServerIpResolve) {  
        this.thriftServerIpResolve = thriftServerIpResolve;  
    }  
  
    public void setThriftServerAddressRegister(ThriftServerAddressRegister thriftServerAddressRegister) {  
        this.thriftServerAddressRegister = thriftServerAddressRegister;  
    }  
  
    @Override  
    public void afterPropertiesSet() throws Exception {  
        if (thriftServerIpResolve == null) {  
            thriftServerIpResolve = new ThriftServerIpLocalNetworkResolve();  
        }  
        String serverIP = thriftServerIpResolve.getServerIp();  
        if (StringUtils.isEmpty(serverIP)) {  
            throw new ThriftException("cant find server ip...");  
        }  
  
        String hostname = serverIP + ":" + port + ":" + weight;  
        Class<?> serviceClass = service.getClass();  
        // 获取实现类接口  
        Class<?>[] interfaces = serviceClass.getInterfaces();  
        if (interfaces.length == 0) {  
            throw new IllegalClassFormatException("service-class should implements Iface");  
        }  
        // reflect,load "Processor";  
        TProcessor processor = null;  
        String serviceName = null;  
        for (Class<?> clazz : interfaces) {  
            String cname = clazz.getSimpleName();  
            if (!cname.equals("Iface")) {  
                continue;  
            }  
            serviceName = clazz.getEnclosingClass().getName();  
            String pname = serviceName + "$Processor";  
            try {  
                ClassLoader classLoader = Thread.currentThread().getContextClassLoader();  
                Class<?> pclass = classLoader.loadClass(pname);  
                if (!TProcessor.class.isAssignableFrom(pclass)) {  
                    continue;  
                }  
                Constructor<?> constructor = pclass.getConstructor(clazz);  
                processor = (TProcessor) constructor.newInstance(service);  
                break;  
            } catch (Exception e) {  
                //  
            }  
        }  
        if (processor == null) {  
            throw new IllegalClassFormatException("service-class should implements Iface");  
        }  
        //需要单独的线程,因为serve方法是阻塞的.  
        serverThread = new ServerThread(processor, port);  
        serverThread.start();  
        // 注册服务  
        if (thriftServerAddressRegister != null) {  
            thriftServerAddressRegister.register(serviceName, version, hostname);  
        }  
  
    }  
    class ServerThread extends Thread {  
        private TServer server;  
        ServerThread(TProcessor processor, int port) throws Exception {  
            TNonblockingServerSocket serverTransport = new TNonblockingServerSocket(port);  
            TThreadedSelectorServer.Args tArgs = new TThreadedSelectorServer.Args(serverTransport);    
            TProcessorFactory processorFactory = new TProcessorFactory(processor);  
            tArgs.processorFactory(processorFactory);  
            tArgs.transportFactory(new TFramedTransport.Factory());    
            tArgs.protocolFactory( new TBinaryProtocol.Factory(true, true));   
            server = new TThreadedSelectorServer(tArgs);  
        }  
  
        @Override  
        public void run(){  
            try{  
                //启动服务  
                server.serve();  
            }catch(Exception e){  
                //  
            }  
        }  
          
        public void stopServer(){  
            server.stop();  
        }  
    }  
      
    public void close() {  
        serverThread.stopServer();  
    }  
}  

猜你喜欢

转载自my.oschina.net/u/1000241/blog/1785713