From 6bfcb2e1f551620dab108b2d893bd3dfad93425a Mon Sep 17 00:00:00 2001 From: Kawin Viriyaprasopsook Date: Mon, 22 Jul 2024 15:26:58 +0700 Subject: [PATCH 01/16] =?UTF-8?q?=E2=9A=A1=EF=B8=8F=20slices.SortFunc=20fo?= =?UTF-8?q?r=20upstreams?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/mod/utils/utils.go | 52 ++++++++++++++++++++++++------------------ src/upstreams.go | 20 ++++++++-------- 2 files changed, 40 insertions(+), 32 deletions(-) diff --git a/src/mod/utils/utils.go b/src/mod/utils/utils.go index a61d5ed..21d2e40 100644 --- a/src/mod/utils/utils.go +++ b/src/mod/utils/utils.go @@ -41,12 +41,12 @@ func SendOK(w http.ResponseWriter) { // Get GET parameter func GetPara(r *http.Request, key string) (string, error) { - keys, ok := r.URL.Query()[key] - if !ok || len(keys[0]) < 1 { + // Get first value from the URL query + value := r.URL.Query().Get(key) + if len(value) == 0 { return "", errors.New("invalid " + key + " given") - } else { - return keys[0], nil } + return value, nil } // Get GET paramter as boolean, accept 1 or true @@ -56,26 +56,29 @@ func GetBool(r *http.Request, key string) (bool, error) { return false, err } - x = strings.TrimSpace(x) - - if x == "1" || strings.ToLower(x) == "true" || strings.ToLower(x) == "on" { + // Convert to lowercase and trim spaces just once to compare + switch strings.ToLower(strings.TrimSpace(x)) { + case "1", "true", "on": return true, nil - } else if x == "0" || strings.ToLower(x) == "false" || strings.ToLower(x) == "off" { + case "0", "false", "off": return false, nil } return false, errors.New("invalid boolean given") } -// Get POST paramter +// Get POST parameter func PostPara(r *http.Request, key string) (string, error) { - r.ParseForm() - x := r.Form.Get(key) - if x == "" { - return "", errors.New("invalid " + key + " given") - } else { - return x, nil + // Try to parse the form + if err := r.ParseForm(); err != nil { + return "", err } + // Get first value from the form + x := r.Form.Get(key) + if len(x) == 0 { + return "", errors.New("invalid " + key + " given") + } + return x, nil } // Get POST paramter as boolean, accept 1 or true @@ -85,11 +88,11 @@ func PostBool(r *http.Request, key string) (bool, error) { return false, err } - x = strings.TrimSpace(x) - - if x == "1" || strings.ToLower(x) == "true" || strings.ToLower(x) == "on" { + // Convert to lowercase and trim spaces just once to compare + switch strings.ToLower(strings.TrimSpace(x)) { + case "1", "true", "on": return true, nil - } else if x == "0" || strings.ToLower(x) == "false" || strings.ToLower(x) == "off" { + case "0", "false", "off": return false, nil } @@ -114,14 +117,19 @@ func PostInt(r *http.Request, key string) (int, error) { func FileExists(filename string) bool { _, err := os.Stat(filename) - if os.IsNotExist(err) { + if err == nil { + // File exists + return true + } else if errors.Is(err, os.ErrNotExist) { + // File does not exist return false } - return true + // Some other error + return false } func IsDir(path string) bool { - if FileExists(path) == false { + if !FileExists(path) { return false } fi, err := os.Stat(path) diff --git a/src/upstreams.go b/src/upstreams.go index 3ab2eab..c05e645 100644 --- a/src/upstreams.go +++ b/src/upstreams.go @@ -1,9 +1,10 @@ package main import ( + "cmp" "encoding/json" "net/http" - "sort" + "slices" "strings" "imuslab.com/zoraxy/mod/dynamicproxy/loadbalance" @@ -33,19 +34,18 @@ func ReverseProxyUpstreamList(w http.ResponseWriter, r *http.Request) { activeUpstreams := targetEndpoint.ActiveOrigins inactiveUpstreams := targetEndpoint.InactiveOrigins - // Sort the upstreams slice by weight, then by origin domain alphabetically - sort.Slice(activeUpstreams, func(i, j int) bool { - if activeUpstreams[i].Weight != activeUpstreams[j].Weight { - return activeUpstreams[i].Weight > activeUpstreams[j].Weight + slices.SortFunc(activeUpstreams, func(i, j *loadbalance.Upstream) int { + if i.Weight != j.Weight { + return cmp.Compare(j.Weight, i.Weight) } - return activeUpstreams[i].OriginIpOrDomain < activeUpstreams[j].OriginIpOrDomain + return cmp.Compare(i.OriginIpOrDomain, j.OriginIpOrDomain) }) - sort.Slice(inactiveUpstreams, func(i, j int) bool { - if inactiveUpstreams[i].Weight != inactiveUpstreams[j].Weight { - return inactiveUpstreams[i].Weight > inactiveUpstreams[j].Weight + slices.SortFunc(inactiveUpstreams, func(i, j *loadbalance.Upstream) int { + if i.Weight != j.Weight { + return cmp.Compare(j.Weight, i.Weight) } - return inactiveUpstreams[i].OriginIpOrDomain < inactiveUpstreams[j].OriginIpOrDomain + return cmp.Compare(i.OriginIpOrDomain, j.OriginIpOrDomain) }) type UpstreamCombinedList struct { From 0dddd1f9e3df0f81f34818e21cb9fd0cabd178f7 Mon Sep 17 00:00:00 2001 From: Kawin Viriyaprasopsook Date: Mon, 22 Jul 2024 15:29:43 +0700 Subject: [PATCH 02/16] =?UTF-8?q?=F0=9F=93=9D=20discribe=20for=20upstream?= =?UTF-8?q?=20sort=20func?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/upstreams.go | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/upstreams.go b/src/upstreams.go index c05e645..dd53c83 100644 --- a/src/upstreams.go +++ b/src/upstreams.go @@ -36,15 +36,19 @@ func ReverseProxyUpstreamList(w http.ResponseWriter, r *http.Request) { inactiveUpstreams := targetEndpoint.InactiveOrigins slices.SortFunc(activeUpstreams, func(i, j *loadbalance.Upstream) int { if i.Weight != j.Weight { + // sort by weight DESC return cmp.Compare(j.Weight, i.Weight) } + // sort by origin ASC return cmp.Compare(i.OriginIpOrDomain, j.OriginIpOrDomain) }) slices.SortFunc(inactiveUpstreams, func(i, j *loadbalance.Upstream) int { if i.Weight != j.Weight { + // sort by weight DESC return cmp.Compare(j.Weight, i.Weight) } + // sort by origin ASC return cmp.Compare(i.OriginIpOrDomain, j.OriginIpOrDomain) }) From bec363ababa22eb4c7f9e968c862f326c50d3130 Mon Sep 17 00:00:00 2001 From: bouroo Date: Mon, 22 Jul 2024 23:39:47 +0700 Subject: [PATCH 03/16] =?UTF-8?q?=E2=9A=A1=EF=B8=8F=20immediate=20return?= =?UTF-8?q?=20if=20single=20upstream?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../dynamicproxy/loadbalance/originPicker.go | 61 +++++++++++-------- src/mod/utils/utils.go | 2 +- src/upstreams.go | 4 +- 3 files changed, 38 insertions(+), 29 deletions(-) diff --git a/src/mod/dynamicproxy/loadbalance/originPicker.go b/src/mod/dynamicproxy/loadbalance/originPicker.go index 51bcc2b..ad5ddc4 100644 --- a/src/mod/dynamicproxy/loadbalance/originPicker.go +++ b/src/mod/dynamicproxy/loadbalance/originPicker.go @@ -102,39 +102,48 @@ func (m *RouteManager) getSessionHandler(r *http.Request, upstreams []*Upstream) /* Functions related to random upstream picking */ // Get a random upstream by the weights defined in Upstream struct, return the upstream, index value and any error func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { - var ret *Upstream - sum := 0 - for _, c := range upstreams { - sum += c.Weight + totalUpstreams := len(upstreams) + if totalUpstreams == 1 { + return upstreams[0], 0, nil } - r, err := intRange(0, sum) - if err != nil { - return ret, -1, err - } - counter := 0 - for _, c := range upstreams { - r -= c.Weight - if r < 0 { - return c, counter, nil - } - counter++ + if totalUpstreams == 0 { + return nil, -1, errors.New("no upstream servers available") } - if ret == nil { - //All fallback - //use the first one that is with weight = 0 - fallbackUpstreams := []*Upstream{} - fallbackUpstreamsOriginalID := []int{} - for ix, upstream := range upstreams { - if upstream.Weight == 0 { - fallbackUpstreams = append(fallbackUpstreams, upstream) - fallbackUpstreamsOriginalID = append(fallbackUpstreamsOriginalID, ix) - } + totalWeight := 0 + fallbackUpstreams := make([]*Upstream, 0) // List of upstreams with weight 0 + fallbackUpstreamsOriginalID := make([]int, 0) + + // Calculate total weight and gather fallbacks + for ix, upstream := range upstreams { + totalWeight += upstream.Weight + if upstream.Weight == 0 { + fallbackUpstreams = append(fallbackUpstreams, upstream) + fallbackUpstreamsOriginalID = append(fallbackUpstreamsOriginalID, ix) + } + } + + if totalWeight == 0 { + // If total weight is 0, fallback to a random upstream with weight 0 + if len(fallbackUpstreams) == 0 { + return nil, -1, errors.New("no valid upstream servers available") } upstreamID := rand.Intn(len(fallbackUpstreams)) return fallbackUpstreams[upstreamID], fallbackUpstreamsOriginalID[upstreamID], nil } - return ret, -1, errors.New("failed to pick an upstream origin server") + + // Generate a random number in the range of total weight + r := rand.Intn(totalWeight) + + // Select upstream based on random number + for i, upstream := range upstreams { + r -= upstream.Weight + if r < 0 { + return upstream, i, nil + } + } + + return nil, -1, errors.New("failed to pick an upstream origin server") } // IntRange returns a random integer in the range from min to max. diff --git a/src/mod/utils/utils.go b/src/mod/utils/utils.go index 21d2e40..2fe1ffd 100644 --- a/src/mod/utils/utils.go +++ b/src/mod/utils/utils.go @@ -199,4 +199,4 @@ func ValidateListeningAddress(address string) bool { } return true -} +} \ No newline at end of file diff --git a/src/upstreams.go b/src/upstreams.go index dd53c83..8241f04 100644 --- a/src/upstreams.go +++ b/src/upstreams.go @@ -34,7 +34,7 @@ func ReverseProxyUpstreamList(w http.ResponseWriter, r *http.Request) { activeUpstreams := targetEndpoint.ActiveOrigins inactiveUpstreams := targetEndpoint.InactiveOrigins - slices.SortFunc(activeUpstreams, func(i, j *loadbalance.Upstream) int { + slices.SortStableFunc(activeUpstreams, func(i, j *loadbalance.Upstream) int { if i.Weight != j.Weight { // sort by weight DESC return cmp.Compare(j.Weight, i.Weight) @@ -43,7 +43,7 @@ func ReverseProxyUpstreamList(w http.ResponseWriter, r *http.Request) { return cmp.Compare(i.OriginIpOrDomain, j.OriginIpOrDomain) }) - slices.SortFunc(inactiveUpstreams, func(i, j *loadbalance.Upstream) int { + slices.SortStableFunc(inactiveUpstreams, func(i, j *loadbalance.Upstream) int { if i.Weight != j.Weight { // sort by weight DESC return cmp.Compare(j.Weight, i.Weight) From d64b1174af4bb0dacef315e139e3ca030e32f900 Mon Sep 17 00:00:00 2001 From: Kawin Viriyaprasopsook Date: Tue, 23 Jul 2024 08:20:59 +0700 Subject: [PATCH 04/16] =?UTF-8?q?=E2=8F=AA=20keep=20compatible=20with=20go?= =?UTF-8?q?=201.20?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/upstreams.go | 24 ++++++++++-------------- 1 file changed, 10 insertions(+), 14 deletions(-) diff --git a/src/upstreams.go b/src/upstreams.go index 8241f04..3ab2eab 100644 --- a/src/upstreams.go +++ b/src/upstreams.go @@ -1,10 +1,9 @@ package main import ( - "cmp" "encoding/json" "net/http" - "slices" + "sort" "strings" "imuslab.com/zoraxy/mod/dynamicproxy/loadbalance" @@ -34,22 +33,19 @@ func ReverseProxyUpstreamList(w http.ResponseWriter, r *http.Request) { activeUpstreams := targetEndpoint.ActiveOrigins inactiveUpstreams := targetEndpoint.InactiveOrigins - slices.SortStableFunc(activeUpstreams, func(i, j *loadbalance.Upstream) int { - if i.Weight != j.Weight { - // sort by weight DESC - return cmp.Compare(j.Weight, i.Weight) + // Sort the upstreams slice by weight, then by origin domain alphabetically + sort.Slice(activeUpstreams, func(i, j int) bool { + if activeUpstreams[i].Weight != activeUpstreams[j].Weight { + return activeUpstreams[i].Weight > activeUpstreams[j].Weight } - // sort by origin ASC - return cmp.Compare(i.OriginIpOrDomain, j.OriginIpOrDomain) + return activeUpstreams[i].OriginIpOrDomain < activeUpstreams[j].OriginIpOrDomain }) - slices.SortStableFunc(inactiveUpstreams, func(i, j *loadbalance.Upstream) int { - if i.Weight != j.Weight { - // sort by weight DESC - return cmp.Compare(j.Weight, i.Weight) + sort.Slice(inactiveUpstreams, func(i, j int) bool { + if inactiveUpstreams[i].Weight != inactiveUpstreams[j].Weight { + return inactiveUpstreams[i].Weight > inactiveUpstreams[j].Weight } - // sort by origin ASC - return cmp.Compare(i.OriginIpOrDomain, j.OriginIpOrDomain) + return inactiveUpstreams[i].OriginIpOrDomain < inactiveUpstreams[j].OriginIpOrDomain }) type UpstreamCombinedList struct { From 97ff48ee705b559cc43f8f74607b1f7bc196cd04 Mon Sep 17 00:00:00 2001 From: Kawin Viriyaprasopsook Date: Tue, 23 Jul 2024 08:29:48 +0700 Subject: [PATCH 05/16] =?UTF-8?q?=F0=9F=94=A5=20origins=20already=20checke?= =?UTF-8?q?d=20before=20getRandomUpstreamByWeight?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/mod/dynamicproxy/loadbalance/originPicker.go | 3 --- 1 file changed, 3 deletions(-) diff --git a/src/mod/dynamicproxy/loadbalance/originPicker.go b/src/mod/dynamicproxy/loadbalance/originPicker.go index ad5ddc4..b74dce8 100644 --- a/src/mod/dynamicproxy/loadbalance/originPicker.go +++ b/src/mod/dynamicproxy/loadbalance/originPicker.go @@ -106,9 +106,6 @@ func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { if totalUpstreams == 1 { return upstreams[0], 0, nil } - if totalUpstreams == 0 { - return nil, -1, errors.New("no upstream servers available") - } totalWeight := 0 fallbackUpstreams := make([]*Upstream, 0) // List of upstreams with weight 0 From d17de5c20090f6bd2d42015ecac46597fe593d0d Mon Sep 17 00:00:00 2001 From: Kawin Viriyaprasopsook Date: Tue, 23 Jul 2024 08:50:10 +0700 Subject: [PATCH 06/16] =?UTF-8?q?=E2=9C=A8=20weighted=20random=20upstream?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../dynamicproxy/loadbalance/originPicker.go | 51 +++++++++++-------- 1 file changed, 30 insertions(+), 21 deletions(-) diff --git a/src/mod/dynamicproxy/loadbalance/originPicker.go b/src/mod/dynamicproxy/loadbalance/originPicker.go index b74dce8..8971184 100644 --- a/src/mod/dynamicproxy/loadbalance/originPicker.go +++ b/src/mod/dynamicproxy/loadbalance/originPicker.go @@ -102,44 +102,53 @@ func (m *RouteManager) getSessionHandler(r *http.Request, upstreams []*Upstream) /* Functions related to random upstream picking */ // Get a random upstream by the weights defined in Upstream struct, return the upstream, index value and any error func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { - totalUpstreams := len(upstreams) - if totalUpstreams == 1 { + // If there is only one upstream, return it + if len(upstreams) == 1 { return upstreams[0], 0, nil } + // Calculate total weight for upstreams with weight > 0 totalWeight := 0 - fallbackUpstreams := make([]*Upstream, 0) // List of upstreams with weight 0 - fallbackUpstreamsOriginalID := make([]int, 0) + fallbackUpstreams := make([]*Upstream, 0) - // Calculate total weight and gather fallbacks - for ix, upstream := range upstreams { - totalWeight += upstream.Weight - if upstream.Weight == 0 { - fallbackUpstreams = append(fallbackUpstreams, upstream) - fallbackUpstreamsOriginalID = append(fallbackUpstreamsOriginalID, ix) + for _, upstream := range upstreams { + if upstream.Weight > 0 { + totalWeight += upstream.Weight + } else { + fallbackUpstreams = append(fallbackUpstreams, upstream) // Collect fallback upstreams } } + // If there are no upstreams with weight > 0, return a fallback upstream if available if totalWeight == 0 { - // If total weight is 0, fallback to a random upstream with weight 0 - if len(fallbackUpstreams) == 0 { - return nil, -1, errors.New("no valid upstream servers available") + if len(fallbackUpstreams) > 0 { + // Randomly select one of the fallback upstreams + index := rand.Intn(len(fallbackUpstreams)) + return fallbackUpstreams[index], index, nil } - upstreamID := rand.Intn(len(fallbackUpstreams)) - return fallbackUpstreams[upstreamID], fallbackUpstreamsOriginalID[upstreamID], nil + // No upstreams available at all + return nil, -1, errors.New("no valid upstream servers available") } - // Generate a random number in the range of total weight - r := rand.Intn(totalWeight) + // Random weight between 0 and total weight + randomWeight := rand.Intn(totalWeight) - // Select upstream based on random number + // Select an upstream based on the random weight for i, upstream := range upstreams { - r -= upstream.Weight - if r < 0 { - return upstream, i, nil + if upstream.Weight > 0 { // Only consider upstreams with weight > 0 + if randomWeight < upstream.Weight { + return upstream, i, nil // Return the selected upstream and its index + } + randomWeight -= upstream.Weight } } + // If we reach here, it means we should return a fallback upstream if available + if len(fallbackUpstreams) > 0 { + index := rand.Intn(len(fallbackUpstreams)) + return fallbackUpstreams[index], index, nil + } + return nil, -1, errors.New("failed to pick an upstream origin server") } From e53c3cf3c4bd81200e85cbc25546dfa157716173 Mon Sep 17 00:00:00 2001 From: Kawin Viriyaprasopsook Date: Wed, 24 Jul 2024 14:47:33 +0700 Subject: [PATCH 07/16] =?UTF-8?q?=E2=9A=A1=EF=B8=8F=20fallbackUpstreams=20?= =?UTF-8?q?with=20preserve=20index?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../dynamicproxy/loadbalance/originPicker.go | 22 +++++++++++++------ 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/src/mod/dynamicproxy/loadbalance/originPicker.go b/src/mod/dynamicproxy/loadbalance/originPicker.go index 8971184..da4423e 100644 --- a/src/mod/dynamicproxy/loadbalance/originPicker.go +++ b/src/mod/dynamicproxy/loadbalance/originPicker.go @@ -107,15 +107,22 @@ func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { return upstreams[0], 0, nil } + // Preserve the index with upstreams + type upstreamWithIndex struct { + Upstream *Upstream + Index int + } + // Calculate total weight for upstreams with weight > 0 totalWeight := 0 - fallbackUpstreams := make([]*Upstream, 0) + fallbackUpstreams := make([]upstreamWithIndex, 0, len(upstreams)) - for _, upstream := range upstreams { + for index, upstream := range upstreams { if upstream.Weight > 0 { totalWeight += upstream.Weight } else { - fallbackUpstreams = append(fallbackUpstreams, upstream) // Collect fallback upstreams + // Collect fallback upstreams + fallbackUpstreams = append(fallbackUpstreams, upstreamWithIndex{upstream, index}) } } @@ -124,7 +131,7 @@ func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { if len(fallbackUpstreams) > 0 { // Randomly select one of the fallback upstreams index := rand.Intn(len(fallbackUpstreams)) - return fallbackUpstreams[index], index, nil + return fallbackUpstreams[index].Upstream, fallbackUpstreams[index].Index, nil } // No upstreams available at all return nil, -1, errors.New("no valid upstream servers available") @@ -134,10 +141,11 @@ func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { randomWeight := rand.Intn(totalWeight) // Select an upstream based on the random weight - for i, upstream := range upstreams { + for index, upstream := range upstreams { if upstream.Weight > 0 { // Only consider upstreams with weight > 0 if randomWeight < upstream.Weight { - return upstream, i, nil // Return the selected upstream and its index + // Return the selected upstream and its index + return upstream, index, nil } randomWeight -= upstream.Weight } @@ -146,7 +154,7 @@ func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { // If we reach here, it means we should return a fallback upstream if available if len(fallbackUpstreams) > 0 { index := rand.Intn(len(fallbackUpstreams)) - return fallbackUpstreams[index], index, nil + return fallbackUpstreams[index].Upstream, fallbackUpstreams[index].Index, nil } return nil, -1, errors.New("failed to pick an upstream origin server") From 8a8ec1cb0be387121ba13b0ac1b450952d80bd53 Mon Sep 17 00:00:00 2001 From: Kawin Viriyaprasopsook Date: Wed, 24 Jul 2024 14:59:48 +0700 Subject: [PATCH 08/16] =?UTF-8?q?=F0=9F=93=9D=20randIndex=20for=20fallback?= =?UTF-8?q?Upstreams=20random?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/mod/dynamicproxy/loadbalance/originPicker.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/mod/dynamicproxy/loadbalance/originPicker.go b/src/mod/dynamicproxy/loadbalance/originPicker.go index da4423e..ad77472 100644 --- a/src/mod/dynamicproxy/loadbalance/originPicker.go +++ b/src/mod/dynamicproxy/loadbalance/originPicker.go @@ -130,8 +130,8 @@ func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { if totalWeight == 0 { if len(fallbackUpstreams) > 0 { // Randomly select one of the fallback upstreams - index := rand.Intn(len(fallbackUpstreams)) - return fallbackUpstreams[index].Upstream, fallbackUpstreams[index].Index, nil + randIndex := rand.Intn(len(fallbackUpstreams)) + return fallbackUpstreams[randIndex].Upstream, fallbackUpstreams[randIndex].Index, nil } // No upstreams available at all return nil, -1, errors.New("no valid upstream servers available") @@ -153,8 +153,8 @@ func getRandomUpstreamByWeight(upstreams []*Upstream) (*Upstream, int, error) { // If we reach here, it means we should return a fallback upstream if available if len(fallbackUpstreams) > 0 { - index := rand.Intn(len(fallbackUpstreams)) - return fallbackUpstreams[index].Upstream, fallbackUpstreams[index].Index, nil + randIndex := rand.Intn(len(fallbackUpstreams)) + return fallbackUpstreams[randIndex].Upstream, fallbackUpstreams[randIndex].Index, nil } return nil, -1, errors.New("failed to pick an upstream origin server") From a5ef6456c65110aef032b37931456d07b0c39b2d Mon Sep 17 00:00:00 2001 From: tobychui Date: Wed, 7 Aug 2024 13:53:43 +0800 Subject: [PATCH 09/16] v3.1.1 init - Fixed path traverse bug in web server file manager - Merged docker container list from main - Updated version code - Merged network status fix from PR - Removed unused comments in dpcore - --- src/main.go | 8 ++++---- src/mod/dynamicproxy/dpcore/dpcore.go | 7 ------- src/mod/webserv/filemanager/filemanager.go | 4 ++++ src/web/components/status.html | 4 ++-- src/web/script/utils.js | 2 +- src/web/snippet/dockerContainersList.html | 19 +++++++++++-------- 6 files changed, 22 insertions(+), 22 deletions(-) diff --git a/src/main.go b/src/main.go index b40637e..e93d4df 100644 --- a/src/main.go +++ b/src/main.go @@ -59,9 +59,9 @@ var enableAutoUpdate = flag.Bool("cfgupgrade", true, "Enable auto config upgrade var ( name = "Zoraxy" - version = "3.1.0" + version = "3.1.1" nodeUUID = "generic" //System uuid, in uuidv4 format - development = false //Set this to false to use embedded web fs + development = true //Set this to false to use embedded web fs bootTime = time.Now().Unix() /* @@ -117,8 +117,8 @@ func SetupCloseHandler() { func ShutdownSeq() { SystemWideLogger.Println("Shutting down " + name) - SystemWideLogger.Println("Closing GeoDB ") - geodbStore.Close() + //SystemWideLogger.Println("Closing GeoDB") + //geodbStore.Close() SystemWideLogger.Println("Closing Netstats Listener") netstatBuffers.Close() SystemWideLogger.Println("Closing Statistic Collector") diff --git a/src/mod/dynamicproxy/dpcore/dpcore.go b/src/mod/dynamicproxy/dpcore/dpcore.go index 54bbaa0..6f870a2 100644 --- a/src/mod/dynamicproxy/dpcore/dpcore.go +++ b/src/mod/dynamicproxy/dpcore/dpcore.go @@ -350,13 +350,6 @@ func (p *ReverseProxy) ProxyHTTP(rw http.ResponseWriter, req *http.Request, rrr } } - //TODO: Figure out a way to proxy for proxmox - //if res.StatusCode == 501 || res.StatusCode == 500 { - // fmt.Println(outreq.Proto, outreq.RemoteAddr, outreq.RequestURI) - // fmt.Println(">>>", outreq.Method, res.Header, res.ContentLength, res.StatusCode) - // fmt.Println(outreq.Header, req.Host) - //} - //Add debug X-Proxy-By tracker res.Header.Set("x-proxy-by", "zoraxy/"+rrr.Version) diff --git a/src/mod/webserv/filemanager/filemanager.go b/src/mod/webserv/filemanager/filemanager.go index 21b6bea..761daef 100644 --- a/src/mod/webserv/filemanager/filemanager.go +++ b/src/mod/webserv/filemanager/filemanager.go @@ -42,6 +42,10 @@ func (fm *FileManager) HandleList(w http.ResponseWriter, r *http.Request) { // Construct the absolute path to the target directory targetDir := filepath.Join(fm.Directory, directory) + // Clean path to prevent path escape #274 + targetDir = filepath.ToSlash(filepath.Clean(targetDir)) + targetDir = strings.ReplaceAll(targetDir, "../", "") + // Open the target directory dirEntries, err := os.ReadDir(targetDir) if err != nil { diff --git a/src/web/components/status.html b/src/web/components/status.html index 0e0d19b..e783ba6 100644 --- a/src/web/components/status.html +++ b/src/web/components/status.html @@ -583,14 +583,14 @@ url: '/api/stats/netstatgraph?array=true', success: function(data){ if (rxValues.length == 0){ - rxValues = JSON.parse(JSON.stringify(data.Rx)); + rxValues.push(...data.Rx); }else{ rxValues.push(data.Rx[dataCount-1]); rxValues.shift(); } if (txValues.length == 0){ - txValues = JSON.parse(JSON.stringify(data.Tx)); + txValues.push(...data.Tx); }else{ txValues.push(data.Tx[dataCount-1]); txValues.shift(); diff --git a/src/web/script/utils.js b/src/web/script/utils.js index 289bd6b..abcc0bb 100644 --- a/src/web/script/utils.js +++ b/src/web/script/utils.js @@ -30,7 +30,7 @@ Object.defineProperty(String.prototype, 'capitalize', { //Add a new function to jquery for ajax override with csrf token injected $.cjax = function(payload){ - let requireTokenMethod = ["POST", "PUT", "DELETE"];; + let requireTokenMethod = ["POST", "PUT", "DELETE"]; if (requireTokenMethod.includes(payload.method) || requireTokenMethod.includes(payload.type)){ //csrf token is required let csrfToken = document.getElementsByTagName("meta")["zoraxy.csrf.Token"].getAttribute("content"); diff --git a/src/web/snippet/dockerContainersList.html b/src/web/snippet/dockerContainersList.html index 0058e3b..c71c09a 100644 --- a/src/web/snippet/dockerContainersList.html +++ b/src/web/snippet/dockerContainersList.html @@ -34,7 +34,7 @@ + \ No newline at end of file diff --git a/src/web/components/rules.html b/src/web/components/rules.html index 2873660..5683c60 100644 --- a/src/web/components/rules.html +++ b/src/web/components/rules.html @@ -30,12 +30,12 @@

New Proxy Rule

You can add more proxy rules to support more site via domain / subdomains

-
+
Support subdomain and wildcard, e.g. s1.mydomain.com or *.test.mydomain.com. Use comma (,) for alias hostnames.
-
+
e.g. 192.168.0.101:8000 or example.com @@ -43,7 +43,7 @@ -
+
@@ -67,7 +67,7 @@ Security
-
+
@@ -154,7 +154,9 @@

- +
+ +


diff --git a/src/web/components/status.html b/src/web/components/status.html index e783ba6..a664cdd 100644 --- a/src/web/components/status.html +++ b/src/web/components/status.html @@ -53,8 +53,10 @@
- - +
+ + +

Network Status

Overall Network I/O in Current Host Server

diff --git a/src/web/components/webserv.html b/src/web/components/webserv.html index ccc073e..8d099b6 100644 --- a/src/web/components/webserv.html +++ b/src/web/components/webserv.html @@ -13,34 +13,35 @@
- -

Web Server Settings

-
-
-
- - +
+

Web Server Settings

+
+
+
+ + +
-
-
-
- - - If this folder do not contains any index files, list the directory of this folder. +
+
+ + + If this folder do not contains any index files, list the directory of this folder. +
+
+
+ + + + The web server root folder can only be changed via startup flags of zoraxy for security reasons. + See the -webserv flag for more details. + +
+
+ + + Use http://127.0.0.1:8081 in proxy rules to access the web server
-
-
- - - - The web server root folder can only be changed via startup flags of zoraxy for security reasons. - See the -webserv flag for more details. - -
-
- - - Use http://127.0.0.1:8081 in proxy rules to access the web server
Changes are saved automatically diff --git a/src/web/img/res/1F310.png b/src/web/img/res/1F310.png new file mode 100644 index 0000000000000000000000000000000000000000..90d92713c882bf17f3fdd7ffa8f3f23b2ed8167c GIT binary patch literal 14288 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 literal 0 HcmV?d00001 diff --git a/src/web/img/res/1F387.png b/src/web/img/res/1F387.png new file mode 100644 index 0000000000000000000000000000000000000000..403c26db6acd44468b4e2d43b5bae3c33871e837 GIT binary patch literal 10479 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 z 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 Uj`-EwV)|(hQPWkeQ?`lte?a-YaR2}S literal 0 HcmV?d00001 diff --git a/src/web/img/res/1F38A.png b/src/web/img/res/1F38A.png new file mode 100644 index 0000000000000000000000000000000000000000..1ecac567d64b79705203785e4542262e97151032 GIT binary patch literal 11303 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 a%LHpe;33769<=cvP)6lX(-=3 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 IWghl_0GsD5jQ{`u literal 0 HcmV?d00001 diff --git a/src/web/img/res/1F500.png b/src/web/img/res/1F500.png new file mode 100644 index 0000000000000000000000000000000000000000..928d8b4dbabedf9bc58ead594510e5a531d4d21e GIT binary patch literal 6042 zcmeHL`8!na`&UXzQt3#NUH9uePfQT{kQ0I@SXfvf26uGK zSXd5w9z5)<`zsYEv*G*3j){?luD-9){>uNZ|8?O1VF%}v3t{3*&&NX zQzM8|3&X$2|A=dKy{U?R;rZ&^=cd-x?sRz4n2Bhkj-hltvt@qPlBgteMZWC}_s?)` zOzoUn_Wh0&|IizWB~g)@gs{%$YY7=&j2euGWS=H0Mz{jKcR$J9bV#iW$+~Wja)Lh2 zf8ed$^Tf2>S0NK`rA~>V1>doLE$LD4_Cx7JuB}b+N3?`g;N^=!B(HY?5u=hC> z@}*HwLh;W4nXUhX9WqvZ>GTL=g3Q*|6bwLiXQj#Omq?nV*+H4E0ZuQ}J}wAl=K&$J z)$3ILpd9jmIDrgQMD5W8+wesC_Y@eJtr@vx;(@+QdO&ydK#}6;b=`s<5FCY?ME`D% za?XUDsa`ikvXb7vr4vt(XwFLciUJIVV*zFJD;t?j+cry_OwSsOraKZRFO%b=ZL{8a z<=0TW|9x%q(m=_X4-09bWaWjr1y7<$Y26G@H&$efl0VeceaA zuAszyW%IN|8Kd$Q9~z*J9&F3^ck&~%+7AfH6lE>cL?)yUman+c&tTnWm)mFefQVBl z;c;}m17p!sdj9G`paK$&6FIcd=8%XWEtcqAyM|V7ol4{8=^ZKh@Fwbw1L>+P%{Xw! z+PQDe+CD16EK&AvzgThirLLg6_HrsSOG@ah2v+WE8QB(3(i+f$2+*Ei(Tmb`A>}sFUjXw z`OBo!_&9TSin^d6VeVOtVGp-@FeSYvK(po{J;F;nGDZ7&p)MjQXuUi3hwt)CP)=c> z8vD-#T;{^OG|KvFhxX90#j1Axe1%n8za8UZR+pEdn@1Fj9uztM^9nO#ereDJ<*_rg zpdNX{y5G}Q==DFCaEy?4IR=d0oAGXV>n=B=pV^J<;_{=$@ihkKA5X)mNJi`glygaT zN|4LRu>nZ}^(tmlg@1O2A1e<0gX(er*#l=}nlc>Qthu-Ahdzi(ZROslVy)bZ&lc#S z*BpP|__(nUGBs_u8?X^OI z5dY8m_RZ<1a-f}ov*`f($JlI1sl!3*EUJ> zzB0_hJ}yEoQx<(?QMnl-K5STj(c2Xm6G)o(oGw!uGy75~m{LFZ=e%eA z$I3(2D}I3;GgQiY5Ohok;lTCoQ3H0J^jF;rTJ84z_%25+*=fT3@V5di5gQ!Jm*d<< zw|YT+VLYYZm95bioqlC?|D!Fu(|)7tX}^bAX;x1-fSc%~*GBF(R+_Bd)RX=nL`__=SN zd+_Phf#aA3HvD$(N9&fWl0lfGWbNZvQI$UxzV@hsy(VL>PJlJ{WSPQ!_gaPifvm8X ziGc{A4R*rZ98v7yDg)N|N5wWo*S9p!jo@dT)bX`JY7^^=81jn-J!l!AFr-Xj$-#<` zmdh=yoiShcG0H<9AoIBZbLHa6^hKFu6_1P}#krta{{WbffCWH-!gWzx3`($t1lqxb zFvUTDUoQVe36259rO(;Qmyi!X=Wb&kJDn0@pBH)ehEWw*Mk!H{JlKhwbO}V60Y#(5 z3cbZ{bHfa0h@zyl%p& z>IEx?kQN}z^R$KT>9rDWeE$lTzH$v#r5*H=(&S{1^uJL+w$U-~p~N;73fU@BUGJq5?-f?}jw0fi<=AG2C-NHLuevR8fK8O&A# zAiH6J*f?-H?MV;G6uB`cvmFn3$;$4{mjxD(MKsfuEXC2nPXtDg#|p?oP}&l`X&Hl> z#wy`%W6Q2m)&pN)t)f(B_Pe!kaaiY9d;a~aqnR{i+7~(=WzCS+0y+wzA7bfCXO<#< zXSNzU9geD=gi0|_?Z5)s;~7QC z*lAbP*lHc+z7}Aqf2?*XRAhZt5ynBJ{7}l6Zb15{_(P@h>D-UPkqn}vwcQ=ykjJDG zsv1DzC+_S*daP-d*7nCkiLg2TPQ)jnyGG$-rbA##oeAE7 z#AF}Q>Dsl&;!3pv#P5ft9o3b$wSlHk3lC}e!B~*!@pjg@x$(iL@ux?=yQ8%DrLjJy zS)k0f>b0+#qUUe^-R17oJZ%{mer#*jK`_vhJt|)zVgUI>vIAcxg}%wtj)6rCxwvjt|5&43dRixX9^y!c4ktdqJm-8R#1;YxV9*L0yGwcG8-JViYjx~E>D3#`Qb zjtqsxsuM!j66Nz1VA>Z6Yxk5)UaAn@=YhEd1rxzVu1UKa8UU6J7MmHe~hv|);D9r?*KU{yibJq$SmP?Ohaf^u$V5;|0nsP=*q3%s&yzZ~B+_5D zEP%iCMC~G;R=XQ2r0JeD6mocwOhE>0=Iw19`^wh_%PM+Jp4`49bY~0F+r~>FfJ93d zR8<0cT!8cg25d?gs+bgQ=si_*Y*{H(m|5)4GAL5KYes4`L29;9Z#1^XBl6t8m^k3g zDU(FRY6Qd|;E=3qE9MmHsOT*I&_q7hPf(WDM$5#~Tkd9CFeVdxs?0w@-1>Sv29H%$ z3Hhxg%hHt3g{3hXX8d~dnj31=BX51=j2CfE|9q%K)TOh7uZi({xZxSh|5Y8eH=UPwhsoE^B7@-cbGO48HRw%f!s|iF<~ZuH1=f9aXq?kE4+H8V}_N#Znsb zB z=Zszk(HUi_-;HM@&{Cr+k~l|@S>C;PXF`r|r2@n@kvjrym5wMD$#f^?lXo8|=LVC` z@4>qn6Rl2x04}Huzs%Zsw#0+OQ;~;EjlP{N&ZN9MZ{AFwUlA1C0QGJ;;9W_5Bnpu{ z-3hjm&_#;XI3-&XMxn+9Wy@-Mn9L-G)fzWlLV=N|TR_-Rg6c$Tk1om5iq5!9p8f(# zEj;!n_488JPrTV~2Ejg@9!k@JVKyUtQNj})d5d&Z6Bx;fuwa^+BT;e>U6N$rAL+M1 z{4m(Whoyd=`{={}@UQ)+7r_Zs(Rli>4PKLUbtNh8m^eBkpG=czGSg_LBSHKXdlIaw zLQWGk$e<`a3t4(a{_|UcmQVNW#$!QTcsdDcP)$d6<5diM-%t+4(61YmW=jMQyiw@5 zCF+63L?Q!h0P}_fYwCNVqILTE+e$)aA7l05@9%`jseZ?xLVA3;Ct97P>I?7($7u>(mjtFk zUtrrY9TLTooNpCFZ*SJMug(Yt$zY%tNs*))0=V-i+6O&>lG;=a@42R1&G&?jm>=zs zDO7}q;<7^Es~9_#;`wF&dJwN}`HCI!?M})%s*77{hsUz(=^W!R{bBnWUv{PB6SfNb zKE{+)9YslE*07`A(SJXKctSVco=u5AyA1Ut-srWSoJI&PgZ`WA>R&n7-WdC?xfI^% zQK1mkGKMZFdukN)uOB2j^lnq>cY5SU15|n$InAMbkA~dFN=E$c6dtJ(L`W|)28}{u zD)j`E5?AWns?~{;PnnjcD4|$cvXYqBpM80e(c0@GOH_BTVLf>J0--ZL#2Z|k}!sWFXjX{O>^6%QmwvSZAmKsS>&2q10F=Fdt= zxR)}mF|XcKMRLt!-gcyo12kx^*n0csX_~!V&-cv}THB{FON=^kBu7J-wh~3ANM7aE z*Tu8dDYB@Rc7m;-XE)=qm|eKCP-KlEq~3^@93}p(6X$Atc4Vt|x%?I-zxG2+DW#61 z()ejrhx6x)t0g4Wn!81MqJO$Rt#;$jjBZ#qm$(sBcS`N-!^`W(4>u8!p~t*ULe|5; z)UJD%he5`-*LII2R4OK-Z*HmSR{D0F9&9aH!mO(~1TXT{q?zikjG8%rCh6LhIb}Iw za>KpP-g_nZW-9p8n3*ilm?Ut^2|wVUmelFiio4=7S>~MdBILeghpQ*;l;XXa<}{_B zM|j$quUq^JwzYWH)y(KM{Szkz*2CZ(>D*&Cepo74g5+jTbs(^rxU>^-B@%vtX{=#r zP}SM3O18_Z|66raGT5|ux+FiL*r50K{kgk>&b9X2QjHFJ!J9jLz2e&YJiSEmP7lc_E?Je@s0)Ryra zE0YB1S#x-Euc;$#+}#xTZTQ`$zE0VV ztJ1YaEryz7?1S?C#x`fCOREF?z1=#|&k%^ITdF|;)!tp7LoYj)6x}hw7wl1l7~HBq z3OF#GzQyEA2h&)i4a-I#?A!rTJt2e#;P*>~GmSYw$7nR@m}~IwmJX0w_7Kzne4nw# zfTHI66P}GBCP5MoXBC6l>H(?qa{D;WBZR91ERdxU`NzTZexPI` zh{aK}_9^7L-OEwT#yF9zC1Vwi?t{@&?x+$*?-z0t3%fJB@T==V(Vh|LB=W4 zG2mY_!E7j6>R%3eoQYs|>cB?~5Qk-}J@r?H`GesFDV{&81^DWeb%9O5mrjkh{Y@}i z?v8d1YML4hr3Iw=%r_Dg%iE|LO<7nrcb%Z7ax%xq!81o%IWRb@M<~I=K{iRi0w2!;8{1wMWBb9sIn8mz%AWo`j$_7{^bYagKY5Cd-aLj;tMGrdnSSXY Ont?7tr&7x?=Klb4WFD*l literal 0 HcmV?d00001 diff --git a/src/web/img/res/1F512.png b/src/web/img/res/1F512.png new file mode 100644 index 0000000000000000000000000000000000000000..5e33b8f362efb451f919d98671413d8a98057df7 GIT binary patch literal 14908 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%0D{YD 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 D`rwFM literal 0 HcmV?d00001 diff --git a/src/web/img/res/1F914.png b/src/web/img/res/1F914.png new file mode 100644 index 0000000000000000000000000000000000000000..f42134a4522b4919ba049f90a31a4f960b7fc23d GIT binary patch literal 12390 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 literal 0 HcmV?d00001 diff --git a/src/web/img/res/2728.png b/src/web/img/res/2728.png new file mode 100644 index 0000000000000000000000000000000000000000..dca06ddf2bb46a94ccfbc4af28a5d94d0d857748 GIT binary patch literal 12276 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 literal 0 HcmV?d00001 diff --git a/src/web/img/res/E25E.png b/src/web/img/res/E25E.png new file mode 100644 index 0000000000000000000000000000000000000000..d3017c5281074a56326a588842e224ed37afd456 GIT binary patch literal 4476 zcmcIndpy(o|EG=;k?Po~3AvWEoMeq?AjiBaujJE31_&SGw-rZES3O z@?=VIP|%6viJ>7O?(W3Bdwurp+vn@MH!UrdN(Rx zURPH)Cp)XOq`10@TUU4e(4pVr;$k-#8P)JX=B4tmFlu>uS%AMki+SlXi+TK^>KM#L z!eQbrce$wrlNHAYb&Y?JpI-G5*`Ri;UO{!q+Q%y&O8O3JEuJ{+aig5)__|-5qx@^9 ze&e$`^`5t(*poHQMDG`^!iKvAd*e%wVpx?sQV#@=<(ZGtZvAV0=8>+z@k?ZdYI$@lLIC-Wy09#lqzbXiC2D%HVd>Hp&&u}@>mD>;m-#OmnV z!u=5~Uupws_JaqWvY*Fk#@CXVae_6H_{Qby@=snjlwEtSrD7@AnPZQnyz)Fr2sQV1 z|1fz_o5VJvn?X4Vm{xQF+vwId*~9$|yL$vDBL=#lc{u+p5gSNgF~+@oLLHrTXy{;l zs(nP`r==dL5&7@)MYs{Jc^`W=r?UYKU6uviyKPv0po~*z5+H~nXrfIGWsf9(qY1(V3SoS5B;p8$>U->~>V>S_ujc%VA-jsFq~I%6VAkn?!Hpt6`e1hlIqk!J>}2B8*{KK$YZlWoA`Q-|Kfb>mz!S^d_Fu+hxk#i#49@T++u3D?t^7RrLi9KcDD2dk_gHvc;2nnNGEmkT>r-G|Xa*6@ zEOcej43&#$N%ib_ERys}LvSO+iYuw!8icRcyo>UoYSxr)S!gEm8cE^VO=>mM7{MV_ ze2a8RAWn}4o|&{Jv7c?AN)}nd)e1RN9z~plG+xqF0I5aF=7My75-)7*mVX=63%E$D z_678)lW9y)x!ePgj^***4KEpD#kr|~2M0uP-UV-5 z;g$xB)UBuIqyUy=4_;KjB%BV5iuJiK0!Gf7iHSsba`Je%$#^Sf83O^DlY*X=73byx zW6!S|@Sxo!ra`%M#bV7nnQ_Z;?awUdULfhTVJg_YD3z!SzoJc$!XqCN8;zHXy>B;FXUS#)nAHuQnA z%rz}+9BEOVBuej_ak%wNL%V+@Lva7F2otCB+wJryCcQ`6qi5Nuf9=bJ-(t?w@)_Sc zjwB*ST7m%izlJK5p>yB7iWDObejX~V51FZUROhH*fhUrRIL#>Sty6DaK4_jHl^%x{ z8FJpef6!L1v}-1=M51P)xw)IORe^_~L(j`@nv8EhsIYaaQrJwheZVY)>F1kRmga5& zU$j;#ocj?k%}Jb&SqR=>IaoY(sb>&Ht{oSEv8vEScJNviaDi(YP!Qp5$0*uta6(YX zRR0|q8wOcFc{(A<$rlkrJA9LdUl-XJWYY?5?Kq0!k_*L`hD~J6?$v$32aH(B4i(i$ zzNJ&^u2I-y*ri?Uxs=S^H`>+VBlSOFD&1uLBY503?aNymn{cvnwe;p`z@I7Wmp0vC z73KGO`ioOBoZlvD6Mh=!=}t4Dp63Mdb$i)D8k?ReJO{tKgI`d02`PD!GI=e%tk~0I73g19*hAN$?b&r@nglWbvpjvl#MhcBHL-XnZjRC~?K8pvA5$$;{#u?R7>DU*k>;CTTs&1EctT@+&42hL$#)MR{Rpr2=cOUzd@IK3E`Da zoCdM^K)1{NKr6QjV{rT!)lk-}$?VOMP6=9UrjcZj!7n|3L&ogQl1{y3*;HwPNTN@i zPb^vB^+k>RDJo0!y* z+`i?U57PNsVP3-hm(u@(>3hUqvHgEL$le~dZKh`cFJs%KB1<~3C?c4ufkT}ryUG_Z za_xTc>PHaq;p~b9+C;o?acFV6III88gcyj)PS3}zxf~~NS(7CU!)DPo4`NsOWd~_}SfaDceH!2yp zVl6t#Y{(;Ye9`f>eHMR0OBD**lI?0-G}Z=zD
+ +
+


@@ -171,6 +177,22 @@
Confirm Exit?
+ +
+

Welcome to Zoraxy Tour

+

This is a simplified tour to show some of what it can do. + Use your keyboard or click the next button to get going.

+
+
+
+

Steps 1 / 9

+
+
+
+ +
+ +