wxz1211 commented on issue #9824:
URL: https://github.com/apache/apisix/issues/9824#issuecomment-1633417470

   > @wxz1211 Please also provide the snippets of lua code changes you did.
   @Revolyssup 
   hi.Here are my changes:
   1:dashboard-->upstream page --->. add new balance type(nacos_traffic) 
   2:Modified file: balance.lua、discovery/nacos/init.lua
   3:A new file named traffic.lua has been added to the balance directory
   
   
   1、dashboard-->upstream page :
   
![image](https://github.com/apache/apisix/assets/11730002/73934370-e565-43db-a1d9-f75eb066066f)
   Upstream added a new field:nacos_profile
   
![image](https://github.com/apache/apisix/assets/11730002/66eebd76-984d-4bbd-9c36-1fb019d2372e)
   lua:
   
   2、Modified file: balance.lua、discovery/nacos/init.lua
   balance.lua:
   
![image](https://github.com/apache/apisix/assets/11730002/338e01b1-f4bf-4be8-96a8-cb7adf9bfc18)
   discovery/nacos/init.lua:
   
![image](https://github.com/apache/apisix/assets/11730002/3c7e6ea7-9e8b-4981-ad04-b887cf83cbeb)
   
   3、A new file named traffic.lua has been added to the balance directory
   ```lua
   local roundrobin  = require("resty.roundrobin")
   local core = require("apisix.core")
   local nkeys = core.table.nkeys
   local pairs = pairs
   local log = core.log
   
   local _M = {}
   
   
   function _M.new(up_nodes, upstream)
       local safe_limit = 0
       log.info("traffic-up_nodes:", core.json.encode(up_nodes))
       log.info("traffic-upstream:", core.json.encode(upstream))
       log.info("upstream-type:", upstream.type)
       local profile = upstream.profile or 'base'
       local processedData = {}
   
       for key, value in pairs(up_nodes) do
           local ipPort, profile = key:match("([^:]+:%d+):([^:]+)")
           log.info("ipPort:", core.json.encode(ipPort))
           log.info("profile:", core.json.encode(profile))        
           if not processedData[profile] then
               processedData[profile] = {}
           end
           processedData[profile][ipPort] = value
       end
       up_nodes = processedData[profile] or processedData['base']
       log.info("processed-node:", core.json.encode(up_nodes))
       if not up_nodes then
           return nil, "up_nodes not exist"
       end
       for _, weight in pairs(up_nodes) do
           -- the weight can be zero
           safe_limit = safe_limit + weight + 1
       end
   
       local picker = roundrobin:new(up_nodes)
       local nodes_count = nkeys(up_nodes)
       return {
           upstream = upstream,
           get = function (ctx)
               if ctx.balancer_tried_servers and 
ctx.balancer_tried_servers_count == nodes_count then
                   return nil, "all upstream servers tried"
               end
   
               local server, err
               for i = 1, safe_limit do
                   server, err = picker:find()
                   if not server then
                       return nil, err
                   end
                   if ctx.balancer_tried_servers then
                       if not ctx.balancer_tried_servers[server] then
                           break
                       end
                   else
                       break
                   end
               end
   
               return server
           end,
           after_balance = function (ctx, before_retry)
               if not before_retry then
                   if ctx.balancer_tried_servers then
                       core.tablepool.release("balancer_tried_servers", 
ctx.balancer_tried_servers)
                       ctx.balancer_tried_servers = nil
                   end
   
                   return nil
               end
   
               if not ctx.balancer_tried_servers then
                   ctx.balancer_tried_servers = 
core.tablepool.fetch("balancer_tried_servers", 0, 2)
               end
   
               ctx.balancer_tried_servers[ctx.balancer_server] = true
               ctx.balancer_tried_servers_count = 
(ctx.balancer_tried_servers_count or 0) + 1
           end,
           before_retry_next_priority = function (ctx)
               if ctx.balancer_tried_servers then
                   core.tablepool.release("balancer_tried_servers", 
ctx.balancer_tried_servers)
                   ctx.balancer_tried_servers = nil
               end
   
               ctx.balancer_tried_servers_count = 0
           end,
       }
   end
   
   
   return _M
   
   ```
   


-- 
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]

Reply via email to