From 8dffe29146f00b8da98b505b41ab374daf093af2 Mon Sep 17 00:00:00 2001 From: Rainer Killinger Date: Mon, 6 Sep 2021 14:36:06 +0200 Subject: [PATCH] fix: handle patch & duplicate versions correctly --- package-lock.json | 32 +++++++++++++++++++------------- package.json | 3 ++- src/main.ts | 31 +++++++++++++++++++++---------- 3 files changed, 42 insertions(+), 24 deletions(-) diff --git a/package-lock.json b/package-lock.json index 59eba65d..d53130d3 100644 --- a/package-lock.json +++ b/package-lock.json @@ -399,6 +399,15 @@ "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" } + }, + "semver": { + "version": "7.3.4", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.4.tgz", + "integrity": "sha512-tCfb2WLjqFAtXn4KEdxIhalnRtoKFN7nAwj0B3ZXCbQloV2tq5eDbcTmT68JJD3nRJq24/XgxtQKFIpQdtvmVw==", + "dev": true, + "requires": { + "lru-cache": "^6.0.0" + } } } }, @@ -587,15 +596,15 @@ } }, "acorn": { - "version": "8.4.1", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.4.1.tgz", - "integrity": "sha512-asabaBSkEKosYKMITunzX177CXxQ4Q8BSSzMTKD+FefUhipQC70gfW5SiUDhYQ3vk8G+81HqQk7Fv9OXwwn9KA==", + "version": "8.5.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.5.0.tgz", + "integrity": "sha512-yXbYeFy+jUuYd3/CDcg2NkIYE991XYX/bje7LmjJigUciaeO1JR4XxXgCIV1/Zc/dRuFEyw1L0pbA+qynJkW5Q==", "dev": true }, "acorn-walk": { - "version": "8.1.1", - "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.1.1.tgz", - "integrity": "sha512-FbJdceMlPHEAWJOILDk1fXD8lnTlEIWFkqtfk+MvmL5q/qlHfN7GEHcsFZWt/Tea9jRNPWUZG4G976nqAAmU9w==", + "version": "8.2.0", + "resolved": "https://registry.npmjs.org/acorn-walk/-/acorn-walk-8.2.0.tgz", + "integrity": "sha512-k+iyHEuPgSw6SbuDpGQM+06HQUa04DZ3o+F6CSzXMvvI5KMvnaEqXe+YVe555R9nn6GPt404fos4wcgpw12SDA==", "dev": true }, "add-stream": { @@ -2053,7 +2062,6 @@ "version": "6.0.0", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", "integrity": "sha512-Jo6dJ04CmSjuznwJSS3pUeWmd/H0ffTlkXXgwZi+eq1UCmqQwCh+eLsYOYCwY991i2Fah4h1BEMCx4qThGbsiA==", - "dev": true, "requires": { "yallist": "^4.0.0" } @@ -2964,10 +2972,9 @@ "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "semver": { - "version": "7.3.4", - "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.4.tgz", - "integrity": "sha512-tCfb2WLjqFAtXn4KEdxIhalnRtoKFN7nAwj0B3ZXCbQloV2tq5eDbcTmT68JJD3nRJq24/XgxtQKFIpQdtvmVw==", - "dev": true, + "version": "7.3.5", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.5.tgz", + "integrity": "sha512-PoeGJYh8HK4BTO/a9Tf6ZG3veo/A7ZVsYrSA6J8ny9nb3B1VrpkuN+z9OE5wfE5p6H4LchYZsegiQgbJD94ZFQ==", "requires": { "lru-cache": "^6.0.0" } @@ -3635,8 +3642,7 @@ "yallist": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/yallist/-/yallist-4.0.0.tgz", - "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==", - "dev": true + "integrity": "sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==" }, "yaml": { "version": "1.10.0", diff --git a/package.json b/package.json index 2ae4df61..a7ddaadc 100644 --- a/package.json +++ b/package.json @@ -11,7 +11,8 @@ "@types/sha1": "1.1.3", "config": "3.3.6", "dockerode": "3.3.0", - "mustache": "4.2.0" + "mustache": "4.2.0", + "semver": "7.3.5" }, "devDependencies": { "@openstapps/configuration": "0.27.0", diff --git a/src/main.ts b/src/main.ts index 0dc6ce5c..0ad601f1 100644 --- a/src/main.ts +++ b/src/main.ts @@ -17,6 +17,7 @@ import {Logger} from '@openstapps/logger'; import Dockerode from 'dockerode'; import {render} from 'mustache'; import {join} from 'path'; +import * as semver from 'semver'; import { asyncReadFile, configFile, @@ -86,26 +87,36 @@ export async function generateUpstreamMap( .map(async (activeVersionRegex) => { const upstreamName = activeVersionRegex.replace(/[\\|.+]/g, '_'); - const activeBackends = containers.filter((container) => { + let activeBackends = containers.filter((container) => { return containerMatchesRegex('backend', new RegExp(activeVersionRegex), container); }); + // .Labels['stapps.version'] is available if (activeBackends.length > 0) { - foundMatchingContainer = true; - if (activeBackends.length > 1) { - throw new Error('Multiple backends for one version found.'); + activeBackends = activeBackends.sort((a, b) => semver.rcompare(a.Labels['stapps.version'],b.Labels['stapps.version'])); + const activeBackendsVersions = activeBackends.map((container) => container.Labels['stapps.version']) + // tslint:disable-next-line: strict-boolean-expressions + .reduce((map, e) => map.set(e, (map.get(e) || 0) + 1), new Map()); + for (const [version, occurrences] of activeBackendsVersions) { + if (occurrences > 1) { + await Logger.error(`Omitting running version ${version} ! Multiple backends with this exact version are running`); + activeBackends = activeBackends.filter((container) => container.Labels['stapps.version'] !== version); + } } - const gateWayOfContainer = await getGatewayOfStAppsBackend(activeBackends[0]); + if (activeBackends.length !== 0) { + // not only dublicates + foundMatchingContainer = true; - if (gateWayOfContainer.length !== 0) { - upstreams += `\nupstream ${upstreamName} {\n server ${gateWayOfContainer};\n}`; + const gateWayOfContainer = await getGatewayOfStAppsBackend(activeBackends[0]); - return ` \"~${activeVersionRegex}\" ${upstreamName};\n`; + if (gateWayOfContainer.length !== 0) { + upstreams += `\nupstream ${upstreamName} {\n server ${gateWayOfContainer};\n}`; + + return ` \"~${activeVersionRegex}\" ${upstreamName};\n`; + } } - - return ` \"~${activeVersionRegex}\" unavailable;\n`; } await Logger.error('No backend for version', activeVersionRegex, 'found');