AlexStocks commented on code in PR #3252:
URL: https://github.com/apache/dubbo-go/pull/3252#discussion_r2971691614
##########
cluster/router/chain/chain.go:
##########
@@ -106,6 +107,85 @@ func (c *RouterChain) copyRouters()
[]router.PriorityRouter {
return ret
}
+// getApplicationName gets the application name from URL with fallback to
SubURL
+func getApplicationName(url *common.URL) string {
+ appName := url.GetParam(constant.ApplicationKey, "")
+ if appName == "" && url.SubURL != nil {
+ appName = url.SubURL.GetParam(constant.ApplicationKey, "")
+ }
+ return appName
+}
+
+// isRouterMatch checks if router configuration matches the current
service/application
+func isRouterMatch(routerCfg *global.RouterConfig, url *common.URL, appName
string) bool {
+ switch routerCfg.Scope {
+ case constant.RouterScopeService:
+ if url.SubURL != nil {
+ return routerCfg.Key == url.SubURL.ServiceKey()
+ }
+ return routerCfg.Key == url.ServiceKey()
+ case constant.RouterScopeApplication:
+ return routerCfg.Key == appName
+ default:
+ logger.Warnf("unknown router scope: %s", routerCfg.Scope)
+ return false
+ }
+}
+
+// injectStaticRouters injects static router configurations into the router
chain.
+// Called after all routers are created to ensure they exist.
+// The injected static configs act as bootstrap state only during
initialization. For the shared
+// static and dynamic lifecycle semantics, see router.StaticConfigSetter.
+func (c *RouterChain) injectStaticRouters(url *common.URL) {
+ staticRoutersAttrAny, ok := url.GetAttribute(constant.RoutersConfigKey)
+ if !ok && url.SubURL != nil {
+ staticRoutersAttrAny, ok =
url.SubURL.GetAttribute(constant.RoutersConfigKey)
+ }
+ if !ok {
+ return
+ }
+ staticRoutersAttr, ok := staticRoutersAttrAny.([]*global.RouterConfig)
+ if !ok {
+ logger.Warnf("failed to type assert routers config: expected
[]*global.RouterConfig, got %T", staticRoutersAttrAny)
+ return
+ }
+ if len(staticRoutersAttr) == 0 {
+ return
+ }
+
+ applicationName := getApplicationName(url)
+
+ for _, routerCfg := range staticRoutersAttr {
+ if routerCfg == nil {
+ continue
+ }
+ if routerCfg.Enabled != nil && !*routerCfg.Enabled {
+ continue
+ }
+ if routerCfg.Valid != nil && !*routerCfg.Valid {
+ continue
+ }
+ if !isRouterMatch(routerCfg, url, applicationName) {
+ continue
+ }
+ c.injectRouterConfig(routerCfg)
+ }
+}
+
+// injectRouterConfig injects router configuration into routers that implement
StaticConfigSetter.
+// Each router decides whether the config applies to it and no-ops if not.
+func (c *RouterChain) injectRouterConfig(routerCfg *global.RouterConfig) {
+ routerCfgCopy := routerCfg.Clone()
+
+ c.mutex.RLock()
+ defer c.mutex.RUnlock()
+ for _, r := range c.routers {
+ if setter, ok := r.(router.StaticConfigSetter); ok {
+ setter.SetStaticConfig(routerCfgCopy.Clone())
Review Comment:
这里做了双重克隆保护配置隔离,但每次都 Clone() 开销较大。如果 RouterConfig 很大或 router
数量多,性能会受影响。建议评估是否真的需要给每个 router 都克隆一次,还是在外层克隆一次后可以安全共享只读引用。
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]