1. Program background

Background: Based on the governance of Dubbo service, whether it supports business-level grayscale publishing and whether it supports route forwarding based on service parameters. For example, when a new version of GIS is released, can it be distinguished by resolved address or partner? At the beginning of version release, only resolution requests from Guangdong province are expected to be sent to the new version, while other address requests still use the old version. Or forward to the new version server according to the request of partners such as UCP(Premium sharing), and other partners still forward to the old version, so as to achieve business-level grayscale release and control the scope of influence of the new version. For example, the OMS system can forward requests from heavyweight customers to a separate server cluster based on partners to ensure high availability.

This paper will combine the above issues with the functions provided by Dubbo and propose a design scheme.

2. Theoretical basis of the scheme

Dubbo’s service invocation schematic:



Before the client initiates an RPC service call, the client first selects a service caller from the list of servers, including the following key roles:

1, the Directory

Dynamic discovery of services, usually based on the registry for dynamic registration and discovery of services, its specific implementation class is RegistryDirectory.

2, the Router

Routing implementation, which means to conduct routing selection among all service provider lists discovered by Directory, that is, to select appropriate service providers according to certain routing rules. Subset of service provider list discovered by Directory can be based on Condition or script (JS script by default). The implementation class is ScriptRouter.

3, LoadBalance

Load balancing mechanism, which is based on load balancing algorithm (random, polling)

And so on, select a service provider from the list of service providers returned from (Directory – >Router) to call the RPC service.

4, Cluster

Cluster (fault tolerance mechanism) is a policy that selects a service provider from the list of service providers based on the load balancing algorithm. After the RPC service is called, the system sends an exception policy, such as failover and failfast.

Grayscale publishing of services, whose goal is to send some requests to the new version server and some requests to the old version server according to the request, is essentially a routing mechanism, that is, through certain conditions to narrow the list of service providers of the service, just match the Router of Dubbo.

For more information about Dubbo’s Router mechanism, please refer to page 46, 47, 48 of the official documentation. For more information about Dubbo’s Router mechanism from a source perspective, please refer to the blog post:Blog.csdn.net/prestigedin…

With theoretical support, the following will be based on the above theory of actual combat.

3. Concrete implementation examples of the scheme

What this sample code needs to do is to request a new version of the DemoService#createUser service whose user organization ID(orgId) is 1 (the last server in the current service extractor list) and all servers except the last server.





Since it is required to be based on request parameters, the routing mechanism based on JS script is presented in this paper. Firstly, the current version of Dubbo-Admin can maintain routing rules based on conditional expressions on the background page, and its interface is as follows:





Note: The current version of Dubbo-admin does not support routing rules based on JS expressions. If you manually create routing rules based on expressions, the routing expressions cannot be listed on the page. The interface is as follows:



3.1 JS script

The following scripts are defined for each project and service based on its own requirements:

/** * The DemoService router is provided separately for different methods. This example uses the DemoSerivce# ResponseResult createUser(User User) method, Route selection based on the user's orgId * @param Invokers * @Param Invocation * @param context * @returns */ function demoService_createUser_router(invokers, invocation, context) { if(invokers == null || invokers.size() < 1) { return invokers; } if(!" CreateUser ". Equals (Invocation. GetMethodName ())) {// If the invocation does not match, return invokers; } var availableInvokers = new java.util.ArrayList(invokers.size()); for (var i=0; i<invokers.size(); If (invokers.get(I).isavailable ()) {availableInvokers.add(invokers.get(I)); } } var invArguments = invocation.getArguments(); If (invArguments = = null | | invArguments. Length = = 0) {/ / if the parameter is empty, not according to the parameters of routing return availableInvokers; } var firstArgument = invArguments[0];} var firstArgument = invArguments[0]; var orgId = firstArgument == null ? "" : firstArgument.getOrgId(); If (orgId = = 1 | | orgId = = "1") {/ / if orgId = = 1, only the last node, the rest of the other nodes var selectInvokers = new Java. Util. The ArrayList (1); selectInvokers.add(availableInvokers.get(availableInvokers.size()-1)); return selectInvokers; } else { var selectInvokers = new java.util.ArrayList(availableInvokers.size()-1); for(var i=0; i<availableInvokers.size()-1; i++) { selectInvokers.add(availableInvokers.get(i)); } return selectInvokers; }}Copy the code

3.2 Registering JS script Routing Rules with the Registry As explained above, dubbo-admin does not support registering routing rules on the interface at present.

Public static void main (String [] args) throws the Exception {URL registryUrl = URL. The valueOf (" zookeeper: / / 127.0.0.1:2181 "); ZookeeperRegistryFactory zookeeperRegistryFactory = new ZookeeperRegistryFactory(); zookeeperRegistryFactory.setZookeeperTransporter(new CuratorZookeeperTransporter()); Registry zookeeperRegistry = (ZookeeperRegistry) zookeeperRegistryFactory.createRegistry(registryUrl); RouterURL URL = URL. The valueOf (" script: / / 0.0.0.0 / com. Alibaba. Dubbo. The demo. The demo Service?category=routers&dynamic=false&enabled=true&fo rce=false&name=demoService_createUser_router&priority= 0&runtime=true"); routerURL = routerURL.addParameter("rule", URL.encode(get_demoService_createUser_router())); zookeeperRegistry.register(routerURL); / / register / / zookeeperRegistry. Unregister (routerURL); // Unregister}Copy the code

Once the above code is run, the URL will be dynamically registered without the need for the service provider to restart and will take effect automatically after the next service invocation (the principle behind this is based on dynamic discovery in the registry). The above example code, I have been in the local environment, has been able to run successfully, and achieve the desired effect, the company project needs to customize its routing script (JS script) according to its own characteristics, special service method parameters (such as the way to obtain partner ID), and routing requirements. 3.3 Summary The above shows the Dubbo service publishing scheme based on business grayscale and the partner-based service isolation mechanism (service invokers are screened based on service invocation business parameters). It mainly shows foot-based routing rules. Please refer to its Demo for routing rules of conditional expressions. Its core theoretical support is the Router provided by Dubbo.


Welcome to add the author micro signal (DINGwPMZ), add group discussion, the author quality column catalog: 1, source analysis RocketMQ column (40 +) 2, source analysis Sentinel column (12 +) 3, source analysis Dubbo column (28 +) 4, source analysis Mybatis column 5, source analysis Netty column (18 +) 6, source analysis JUC column Source code analysis (MyCat) for Elasticjob