From ec31f0d17678b837df7750a72a9866d86823ac1e Mon Sep 17 00:00:00 2001 From: chronolaw Date: Fri, 28 Jul 2023 14:45:37 +0800 Subject: [PATCH 1/8] afterHostUpdate --- kong/runloop/balancer/round_robin.lua | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index 674c32fb711b..75f70855287a 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -29,7 +29,6 @@ end function roundrobin_algorithm:afterHostUpdate() - local new_wheel = {} local total_points = 0 local total_weight = 0 local divisor = 0 @@ -37,9 +36,11 @@ function roundrobin_algorithm:afterHostUpdate() local targets = self.balancer.targets or {} -- calculate the gcd to find the proportional weight of each address - for _, target in ipairs(targets) do - for _, address in ipairs(target.addresses) do - local address_weight = address.weight + for i = 1, #targets do + local addresses = targets[i].addresses + + for j = 1, #addresses do + local address_weight = addresses[j].weight divisor = gcd(divisor, address_weight) total_weight = total_weight + address_weight end @@ -56,11 +57,19 @@ function roundrobin_algorithm:afterHostUpdate() end -- add all addresses to the wheel - for _, targets in ipairs(targets) do - for _, address in ipairs(targets.addresses) do + local new_wheel = {} + local idx = 1 + + for i = 1, #targets do + local addresses = targets[i].addresses + + for j = 1, #addresses do + local address = addresses[j] local address_points = address.weight / divisor + for _ = 1, address_points do - new_wheel[#new_wheel + 1] = address + new_wheel[idx] = address + idx = idx + 1 end end end From ebcb970a825ad0de5bfa876a52d8d58e0fa8f235 Mon Sep 17 00:00:00 2001 From: chronolaw Date: Fri, 28 Jul 2023 14:57:00 +0800 Subject: [PATCH 2/8] getPeer --- kong/runloop/balancer/round_robin.lua | 54 ++++++++++++++++----------- 1 file changed, 32 insertions(+), 22 deletions(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index 75f70855287a..1e1a683a3f45 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -84,6 +84,7 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) if handle then -- existing handle, so it's a retry handle.retryCount = handle.retryCount + 1 + else -- no handle, so this is a first try handle = {} -- self:getHandle() -- no GC specific handler needed @@ -91,8 +92,7 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) end local starting_pointer = self.pointer - local address - local ip, port, hostname + repeat self.pointer = self.pointer + 1 @@ -100,29 +100,39 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) self.pointer = 1 end - address = self.wheel[self.pointer] - if address ~= nil and address.available and not address.disabled then - ip, port, hostname = balancers.getAddressPeer(address, cacheOnly) - if ip then - -- success, update handle - handle.address = address - return ip, port, hostname, handle - - elseif port == balancers.errors.ERR_DNS_UPDATED then - -- if healty we just need to try again - if not self.balancer.healthy then - return nil, balancers.errors.ERR_BALANCER_UNHEALTHY - end - elseif port == balancers.errors.ERR_ADDRESS_UNAVAILABLE then - ngx.log(ngx.DEBUG, "found address but it was unavailable. ", - " trying next one.") - else - -- an unknown error occurred - return nil, port + local address = self.wheel[self.pointer] + if not address or not address.available or address.disabled then + goto continue + end + + -- address ~= nil and address.available and not address.disabled + + local ip, port, hostname = balancers.getAddressPeer(address, cacheOnly) + + if ip then + -- success, update handle + handle.address = address + return ip, port, hostname, handle + end + + -- no ip, port is an error hint + if port == balancers.errors.ERR_DNS_UPDATED then + -- if healthy we just need to try again + if not self.balancer.healthy then + return nil, balancers.errors.ERR_BALANCER_UNHEALTHY end + elseif port == balancers.errors.ERR_ADDRESS_UNAVAILABLE then + ngx.log(ngx.DEBUG, "found address but it was unavailable. ", + " trying next one.") + + else + -- an unknown error occurred + return nil, port end + ::continue:: + until self.pointer == starting_pointer return nil, balancers.errors.ERR_NO_PEERS_AVAILABLE @@ -130,7 +140,7 @@ end function roundrobin_algorithm.new(opts) - assert(type(opts) == "table", "Expected an options table, but got: "..type(opts)) + assert(type(opts) == "table", "Expected an options table, but got: " .. type(opts)) local balancer = opts.balancer From d8b096b9842edd91b4751e20f6405c8d4d1cdd4e Mon Sep 17 00:00:00 2001 From: chronolaw Date: Fri, 28 Jul 2023 16:53:50 +0800 Subject: [PATCH 3/8] fix goto continue --- kong/runloop/balancer/round_robin.lua | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index 1e1a683a3f45..ddbc89c83663 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -92,6 +92,8 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) end local starting_pointer = self.pointer + local address + local ip, port, hostname repeat self.pointer = self.pointer + 1 @@ -100,14 +102,14 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) self.pointer = 1 end - local address = self.wheel[self.pointer] + address = self.wheel[self.pointer] if not address or not address.available or address.disabled then goto continue end -- address ~= nil and address.available and not address.disabled - local ip, port, hostname = balancers.getAddressPeer(address, cacheOnly) + ip, port, hostname = balancers.getAddressPeer(address, cacheOnly) if ip then -- success, update handle From 1911d8880529cd5fe9f70fad3daa78e5b42660b5 Mon Sep 17 00:00:00 2001 From: chronolaw Date: Fri, 28 Jul 2023 18:32:13 +0800 Subject: [PATCH 4/8] balancers.errors.ERR_DNS_UPDATED --- kong/runloop/balancer/round_robin.lua | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index ddbc89c83663..db9653900d62 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -118,13 +118,18 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) end -- no ip, port is an error hint + if port == balancers.errors.ERR_DNS_UPDATED then -- if healthy we just need to try again - if not self.balancer.healthy then - return nil, balancers.errors.ERR_BALANCER_UNHEALTHY + if self.balancer.healthy then + goto continue end - elseif port == balancers.errors.ERR_ADDRESS_UNAVAILABLE then + -- not healthy + return nil, balancers.errors.ERR_BALANCER_UNHEALTHY + end + + if port == balancers.errors.ERR_ADDRESS_UNAVAILABLE then ngx.log(ngx.DEBUG, "found address but it was unavailable. ", " trying next one.") From 5f24e0472c45b607ed29817047ca329fa12fcf63 Mon Sep 17 00:00:00 2001 From: chronolaw Date: Fri, 28 Jul 2023 18:34:50 +0800 Subject: [PATCH 5/8] ERR_ADDRESS_UNAVAILABLE --- kong/runloop/balancer/round_robin.lua | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index db9653900d62..62e2a6a00dc1 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -132,12 +132,12 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) if port == balancers.errors.ERR_ADDRESS_UNAVAILABLE then ngx.log(ngx.DEBUG, "found address but it was unavailable. ", " trying next one.") - - else - -- an unknown error occurred - return nil, port + goto continue end + -- an unknown error occurred + return nil, port + ::continue:: until self.pointer == starting_pointer From 699f499914f6af6176a8f89cbe3e565c82ee72bd Mon Sep 17 00:00:00 2001 From: chronolaw Date: Fri, 28 Jul 2023 19:55:23 +0800 Subject: [PATCH 6/8] fix return --- kong/runloop/balancer/round_robin.lua | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index 62e2a6a00dc1..88bc869d22e5 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -136,7 +136,7 @@ function roundrobin_algorithm:getPeer(cacheOnly, handle, hashValue) end -- an unknown error occurred - return nil, port + do return nil, port end ::continue:: From 82d833969778f4d6f37144c7178a805b57a915fe Mon Sep 17 00:00:00 2001 From: chronolaw Date: Fri, 11 Aug 2023 09:34:42 +0800 Subject: [PATCH 7/8] ipairs again --- kong/runloop/balancer/round_robin.lua | 16 +++++----------- 1 file changed, 5 insertions(+), 11 deletions(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index 88bc869d22e5..dfd41e81a45d 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -36,11 +36,9 @@ function roundrobin_algorithm:afterHostUpdate() local targets = self.balancer.targets or {} -- calculate the gcd to find the proportional weight of each address - for i = 1, #targets do - local addresses = targets[i].addresses - - for j = 1, #addresses do - local address_weight = addresses[j].weight + for _, target in ipairs(targets) do + for _, address in ipairs(target.addresses) do + local address_weight = address.weight divisor = gcd(divisor, address_weight) total_weight = total_weight + address_weight end @@ -60,13 +58,9 @@ function roundrobin_algorithm:afterHostUpdate() local new_wheel = {} local idx = 1 - for i = 1, #targets do - local addresses = targets[i].addresses - - for j = 1, #addresses do - local address = addresses[j] + for _, targets in ipairs(targets) do + for _, address in ipairs(targets.addresses) do local address_points = address.weight / divisor - for _ = 1, address_points do new_wheel[idx] = address idx = idx + 1 From cdf21305f036f4920c8add88bee0cd10a47297e4 Mon Sep 17 00:00:00 2001 From: chronolaw Date: Tue, 22 Aug 2023 14:37:22 +0800 Subject: [PATCH 8/8] typo fix: target --- kong/runloop/balancer/round_robin.lua | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/kong/runloop/balancer/round_robin.lua b/kong/runloop/balancer/round_robin.lua index dfd41e81a45d..0dd0e96904ab 100644 --- a/kong/runloop/balancer/round_robin.lua +++ b/kong/runloop/balancer/round_robin.lua @@ -58,8 +58,8 @@ function roundrobin_algorithm:afterHostUpdate() local new_wheel = {} local idx = 1 - for _, targets in ipairs(targets) do - for _, address in ipairs(targets.addresses) do + for _, target in ipairs(targets) do + for _, address in ipairs(target.addresses) do local address_points = address.weight / divisor for _ = 1, address_points do new_wheel[idx] = address