mirror of https://github.com/coder/code-server.git
Update dependencies and force-update qs (#6440)
* Update dependencies and force-update qs This is mainly an attempt to get rid of as many resolutions as possible since it seems they are unnecessary except for qs (according to yarn/npm audit). For qs use 6.9.7 since Express is using 6.9.6 and that matches the most closely. Also add overrides since this is npm's version of yarn's resolutions and we need it for the shrinkwrap to generate with the right dependencies. Decided to keep pinning @types/node as well although I am not sure it is necessary. Express is pulling in v20 types. Since this is development-only we only need it in resolutions. * Run formatter Some rules seem to have changed with the dependency updates. * Replace deprecated bodyParser.json() usage * Audit npm shrinkwrap as well * Skip installing dependencies in audit It seems the tools only require the lock files. * Fix tests when using ipv6 * Add missing openssl dependency to flake
This commit is contained in:
parent
47ee7ae670
commit
acc50a5d36
|
@ -31,7 +31,7 @@ jobs:
|
||||||
uses: actions/checkout@v3
|
uses: actions/checkout@v3
|
||||||
|
|
||||||
- name: Run prettier with actionsx/prettier
|
- name: Run prettier with actionsx/prettier
|
||||||
uses: actionsx/prettier@v2
|
uses: actionsx/prettier@v3
|
||||||
with:
|
with:
|
||||||
args: --check --loglevel=warn .
|
args: --check --loglevel=warn .
|
||||||
|
|
||||||
|
|
|
@ -34,21 +34,12 @@ jobs:
|
||||||
with:
|
with:
|
||||||
node-version: "18"
|
node-version: "18"
|
||||||
|
|
||||||
- name: Fetch dependencies from cache
|
- name: Audit yarn for vulnerabilities
|
||||||
id: cache-yarn
|
run: yarn audit
|
||||||
uses: actions/cache@v3
|
if: success()
|
||||||
with:
|
|
||||||
path: "**/node_modules"
|
|
||||||
key: yarn-build-${{ hashFiles('**/yarn.lock') }}
|
|
||||||
restore-keys: |
|
|
||||||
yarn-build-
|
|
||||||
|
|
||||||
- name: Install dependencies
|
- name: Audit npm for vulnerabilities
|
||||||
if: steps.cache-yarn.outputs.cache-hit != 'true'
|
run: npm shrinkwrap && npm audit
|
||||||
run: SKIP_SUBMODULE_DEPS=1 yarn --frozen-lockfile
|
|
||||||
|
|
||||||
- name: Audit for vulnerabilities
|
|
||||||
run: yarn _audit
|
|
||||||
if: success()
|
if: success()
|
||||||
|
|
||||||
trivy-scan-repo:
|
trivy-scan-repo:
|
||||||
|
|
|
@ -12,7 +12,7 @@
|
||||||
in {
|
in {
|
||||||
devShells.default = pkgs.mkShell {
|
devShells.default = pkgs.mkShell {
|
||||||
nativeBuildInputs = with pkgs; [
|
nativeBuildInputs = with pkgs; [
|
||||||
nodejs yarn' python3 pkg-config git rsync jq moreutils quilt bats
|
nodejs yarn' python3 pkg-config git rsync jq moreutils quilt bats openssl
|
||||||
];
|
];
|
||||||
buildInputs = with pkgs; (lib.optionals (!stdenv.isDarwin) [ libsecret libkrb5 ]
|
buildInputs = with pkgs; (lib.optionals (!stdenv.isDarwin) [ libsecret libkrb5 ]
|
||||||
++ (with xorg; [ libX11 libxkbfile ])
|
++ (with xorg; [ libX11 libxkbfile ])
|
||||||
|
|
101
package.json
101
package.json
|
@ -38,75 +38,62 @@
|
||||||
},
|
},
|
||||||
"main": "out/node/entry.js",
|
"main": "out/node/entry.js",
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@schemastore/package": "^0.0.6",
|
"@schemastore/package": "^0.0.10",
|
||||||
"@types/compression": "^1.7.0",
|
"@types/compression": "^1.7.3",
|
||||||
"@types/cookie-parser": "^1.4.2",
|
"@types/cookie-parser": "^1.4.4",
|
||||||
"@types/express": "^4.17.8",
|
"@types/express": "^4.17.17",
|
||||||
"@types/http-proxy": "^1.17.4",
|
"@types/http-proxy": "1.17.7",
|
||||||
"@types/js-yaml": "^4.0.0",
|
"@types/js-yaml": "^4.0.6",
|
||||||
"@types/node": "^18.0.0",
|
"@types/node": "^18.0.0",
|
||||||
"@types/pem": "^1.9.5",
|
"@types/pem": "^1.14.1",
|
||||||
"@types/proxy-from-env": "^1.0.1",
|
"@types/proxy-from-env": "^1.0.1",
|
||||||
"@types/safe-compare": "^1.1.0",
|
"@types/safe-compare": "^1.1.0",
|
||||||
"@types/semver": "^7.1.0",
|
"@types/semver": "^7.5.2",
|
||||||
"@types/trusted-types": "^2.0.2",
|
"@types/trusted-types": "^2.0.4",
|
||||||
"@types/ws": "^8.5.3",
|
"@types/ws": "^8.5.5",
|
||||||
"@typescript-eslint/eslint-plugin": "^5.41.0",
|
"@typescript-eslint/eslint-plugin": "^6.7.2",
|
||||||
"@typescript-eslint/parser": "^5.41.0",
|
"@typescript-eslint/parser": "^6.7.2",
|
||||||
"audit-ci": "^6.0.0",
|
"audit-ci": "^6.6.1",
|
||||||
"doctoc": "2.2.1",
|
"doctoc": "^2.2.1",
|
||||||
"eslint": "^8.26.0",
|
"eslint": "^8.49.0",
|
||||||
"eslint-config-prettier": "^8.5.0",
|
"eslint-config-prettier": "^9.0.0",
|
||||||
"eslint-import-resolver-typescript": "^3.5.2",
|
"eslint-import-resolver-typescript": "^3.6.0",
|
||||||
"eslint-plugin-import": "^2.26.0",
|
"eslint-plugin-import": "^2.28.1",
|
||||||
"eslint-plugin-prettier": "^4.2.1",
|
"eslint-plugin-prettier": "^5.0.0",
|
||||||
"prettier": "2.8.0",
|
"prettier": "^3.0.3",
|
||||||
"prettier-plugin-sh": "^0.12.8",
|
"prettier-plugin-sh": "^0.13.1",
|
||||||
"ts-node": "^10.0.0",
|
"ts-node": "^10.9.1",
|
||||||
"typescript": "^5.0.4"
|
"typescript": "^5.2.2"
|
||||||
},
|
|
||||||
"resolutions": {
|
|
||||||
"ansi-regex": "^5.0.1",
|
|
||||||
"normalize-package-data": "^5.0.0",
|
|
||||||
"doctoc/underscore": "^1.13.1",
|
|
||||||
"doctoc/**/trim": "^1.0.0",
|
|
||||||
"postcss": "^8.2.1",
|
|
||||||
"browserslist": "^4.16.5",
|
|
||||||
"safe-buffer": "^5.1.1",
|
|
||||||
"vfile-message": "^2.0.2",
|
|
||||||
"tar": "^6.1.9",
|
|
||||||
"path-parse": "^1.0.7",
|
|
||||||
"vm2": "^3.9.11",
|
|
||||||
"follow-redirects": "^1.14.8",
|
|
||||||
"node-fetch": "^2.6.7",
|
|
||||||
"nanoid": "^3.1.31",
|
|
||||||
"minimist": "npm:minimist-lite@2.2.1",
|
|
||||||
"glob-parent": "^6.0.1",
|
|
||||||
"@types/node": "^18.0.0",
|
|
||||||
"qs": "^6.7.3"
|
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@coder/logger": "^3.0.0",
|
"@coder/logger": "^3.0.1",
|
||||||
"argon2": "0.31.0",
|
"argon2": "^0.31.1",
|
||||||
"compression": "^1.7.4",
|
"compression": "^1.7.4",
|
||||||
"cookie-parser": "^1.4.5",
|
"cookie-parser": "^1.4.6",
|
||||||
"env-paths": "^2.2.0",
|
"env-paths": "^2.2.1",
|
||||||
"express": "5.0.0-alpha.8",
|
"express": "5.0.0-alpha.8",
|
||||||
"http-proxy": "^1.18.0",
|
"http-proxy": "^1.18.1",
|
||||||
"httpolyglot": "^0.1.2",
|
"httpolyglot": "^0.1.2",
|
||||||
"i18next": "^23.2.11",
|
"i18next": "^23.5.1",
|
||||||
"js-yaml": "^4.0.0",
|
"js-yaml": "^4.1.0",
|
||||||
"limiter": "^2.1.0",
|
"limiter": "^2.1.0",
|
||||||
"pem": "^1.14.2",
|
"pem": "^1.14.8",
|
||||||
"proxy-agent": "^6.2.1",
|
"proxy-agent": "^6.3.1",
|
||||||
"qs": "6.11.0",
|
"qs": "6.9.7",
|
||||||
"rotating-file-stream": "^3.0.0",
|
"rotating-file-stream": "^3.1.1",
|
||||||
"safe-buffer": "^5.1.1",
|
"safe-buffer": "^5.2.1",
|
||||||
"safe-compare": "^1.1.4",
|
"safe-compare": "^1.1.4",
|
||||||
"semver": "^7.1.3",
|
"semver": "^7.5.4",
|
||||||
"ws": "^8.0.0",
|
"ws": "^8.14.2",
|
||||||
"xdg-basedir": "^4.0.0"
|
"xdg-basedir": "^4.0.0"
|
||||||
},
|
},
|
||||||
|
"resolutions": {
|
||||||
|
"@types/node": "^18.0.0",
|
||||||
|
"qs": "6.9.7"
|
||||||
|
},
|
||||||
|
"overrides": {
|
||||||
|
"qs": "6.9.7"
|
||||||
|
},
|
||||||
"bin": {
|
"bin": {
|
||||||
"code-server": "out/node/entry.js"
|
"code-server": "out/node/entry.js"
|
||||||
},
|
},
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
<!DOCTYPE html>
|
<!doctype html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
<meta charset="utf-8" />
|
<meta charset="utf-8" />
|
||||||
|
|
|
@ -46,7 +46,9 @@ button {
|
||||||
.card-box {
|
.card-box {
|
||||||
background-color: rgb(250, 253, 258);
|
background-color: rgb(250, 253, 258);
|
||||||
border-radius: 5px;
|
border-radius: 5px;
|
||||||
box-shadow: rgba(60, 66, 87, 0.117647) 0px 7px 14px 0px, rgba(0, 0, 0, 0.117647) 0px 3px 6px 0px;
|
box-shadow:
|
||||||
|
rgba(60, 66, 87, 0.117647) 0px 7px 14px 0px,
|
||||||
|
rgba(0, 0, 0, 0.117647) 0px 3px 6px 0px;
|
||||||
max-width: 650px;
|
max-width: 650px;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
<!DOCTYPE html>
|
<!doctype html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
<meta charset="utf-8" />
|
<meta charset="utf-8" />
|
||||||
|
|
|
@ -14,7 +14,11 @@ export enum HttpCode {
|
||||||
* used in the HTTP response.
|
* used in the HTTP response.
|
||||||
*/
|
*/
|
||||||
export class HttpError extends Error {
|
export class HttpError extends Error {
|
||||||
public constructor(message: string, public readonly statusCode: HttpCode, public readonly details?: object) {
|
public constructor(
|
||||||
|
message: string,
|
||||||
|
public readonly statusCode: HttpCode,
|
||||||
|
public readonly details?: object,
|
||||||
|
) {
|
||||||
super(message)
|
super(message)
|
||||||
this.name = this.constructor.name
|
this.name = this.constructor.name
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,10 @@ export class Heart {
|
||||||
private heartbeatInterval = 60000
|
private heartbeatInterval = 60000
|
||||||
public lastHeartbeat = 0
|
public lastHeartbeat = 0
|
||||||
|
|
||||||
public constructor(private readonly heartbeatPath: string, private readonly isActive: () => Promise<boolean>) {
|
public constructor(
|
||||||
|
private readonly heartbeatPath: string,
|
||||||
|
private readonly isActive: () => Promise<boolean>,
|
||||||
|
) {
|
||||||
this.beat = this.beat.bind(this)
|
this.beat = this.beat.bind(this)
|
||||||
this.alive = this.alive.bind(this)
|
this.alive = this.alive.bind(this)
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
import i18next, { init } from "i18next"
|
import i18next, { init } from "i18next"
|
||||||
import * as en from "./locales/en.json"
|
import * as en from "./locales/en.json"
|
||||||
|
import * as ja from "./locales/ja.json"
|
||||||
import * as th from "./locales/th.json"
|
import * as th from "./locales/th.json"
|
||||||
import * as zhCn from "./locales/zh-cn.json"
|
import * as zhCn from "./locales/zh-cn.json"
|
||||||
import * as ja from "./locales/ja.json"
|
|
||||||
init({
|
init({
|
||||||
lng: "en",
|
lng: "en",
|
||||||
fallbackLng: "en", // language to use if translations in user language are not available.
|
fallbackLng: "en", // language to use if translations in user language are not available.
|
||||||
|
|
|
@ -78,7 +78,10 @@ type ChildMessage = RelaunchMessage | ChildHandshakeMessage
|
||||||
type ParentMessage = ParentHandshakeMessage
|
type ParentMessage = ParentHandshakeMessage
|
||||||
|
|
||||||
class ProcessError extends Error {
|
class ProcessError extends Error {
|
||||||
public constructor(message: string, public readonly code: number | undefined) {
|
public constructor(
|
||||||
|
message: string,
|
||||||
|
public readonly code: number | undefined,
|
||||||
|
) {
|
||||||
super(message)
|
super(message)
|
||||||
this.name = this.constructor.name
|
this.name = this.constructor.name
|
||||||
Error.captureStackTrace(this, this.constructor)
|
Error.captureStackTrace(this, this.constructor)
|
||||||
|
|
|
@ -269,7 +269,10 @@ export class CodeServer {
|
||||||
export class CodeServerPage {
|
export class CodeServerPage {
|
||||||
private readonly editorSelector = "div.monaco-workbench"
|
private readonly editorSelector = "div.monaco-workbench"
|
||||||
|
|
||||||
constructor(private readonly codeServer: CodeServer, public readonly page: Page) {
|
constructor(
|
||||||
|
private readonly codeServer: CodeServer,
|
||||||
|
public readonly page: Page,
|
||||||
|
) {
|
||||||
this.page.on("console", (message) => {
|
this.page.on("console", (message) => {
|
||||||
this.codeServer.logger.debug(message.text())
|
this.codeServer.logger.debug(message.text())
|
||||||
})
|
})
|
||||||
|
|
|
@ -92,7 +92,7 @@ describe("createApp", () => {
|
||||||
app.dispose()
|
app.dispose()
|
||||||
}
|
}
|
||||||
|
|
||||||
expect(() => masterBall()).rejects.toThrow(`listen EACCES: permission denied 127.0.0.1:${port}`)
|
expect(() => masterBall()).rejects.toThrow("listen EACCES: permission denied")
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should unlink a socket before listening on the socket", async () => {
|
it("should unlink a socket before listening on the socket", async () => {
|
||||||
|
|
|
@ -1,4 +1,3 @@
|
||||||
import * as bodyParser from "body-parser"
|
|
||||||
import * as express from "express"
|
import * as express from "express"
|
||||||
import * as http from "http"
|
import * as http from "http"
|
||||||
import nodeFetch from "node-fetch"
|
import nodeFetch from "node-fetch"
|
||||||
|
@ -110,7 +109,7 @@ describe("proxy", () => {
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should allow post bodies", async () => {
|
it("should allow post bodies", async () => {
|
||||||
e.use(bodyParser.json({ strict: false }))
|
e.use(express.json({ strict: false }))
|
||||||
e.post("/wsup", (req, res) => {
|
e.post("/wsup", (req, res) => {
|
||||||
res.json(req.body)
|
res.json(req.body)
|
||||||
})
|
})
|
||||||
|
@ -127,7 +126,7 @@ describe("proxy", () => {
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should handle bad requests", async () => {
|
it("should handle bad requests", async () => {
|
||||||
e.use(bodyParser.json({ strict: false }))
|
e.use(express.json({ strict: false }))
|
||||||
e.post("/wsup", (req, res) => {
|
e.post("/wsup", (req, res) => {
|
||||||
res.json(req.body)
|
res.json(req.body)
|
||||||
})
|
})
|
||||||
|
@ -154,7 +153,7 @@ describe("proxy", () => {
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should handle errors", async () => {
|
it("should handle errors", async () => {
|
||||||
e.use(bodyParser.json({ strict: false }))
|
e.use(express.json({ strict: false }))
|
||||||
e.post("/wsup", (req, res) => {
|
e.post("/wsup", (req, res) => {
|
||||||
throw new Error("BROKEN")
|
throw new Error("BROKEN")
|
||||||
})
|
})
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
<!DOCTYPE html>
|
<!doctype html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8" />
|
<meta charset="UTF-8" />
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
import { logger } from "@coder/logger"
|
import { logger } from "@coder/logger"
|
||||||
import * as http from "http"
|
import * as http from "http"
|
||||||
import { AddressInfo } from "net"
|
|
||||||
import * as path from "path"
|
import * as path from "path"
|
||||||
|
import { ensureAddress } from "../../../src/node/app"
|
||||||
import { SettingsProvider, UpdateSettings } from "../../../src/node/settings"
|
import { SettingsProvider, UpdateSettings } from "../../../src/node/settings"
|
||||||
import { LatestResponse, UpdateProvider } from "../../../src/node/update"
|
import { LatestResponse, UpdateProvider } from "../../../src/node/update"
|
||||||
import { clean, isAddressInfo, mockLogger, tmpdir } from "../../utils/helpers"
|
import { clean, mockLogger, tmpdir } from "../../utils/helpers"
|
||||||
|
|
||||||
describe("update", () => {
|
describe("update", () => {
|
||||||
let version = "1.0.0"
|
let version = "1.0.0"
|
||||||
|
@ -79,7 +79,6 @@ describe("update", () => {
|
||||||
}
|
}
|
||||||
|
|
||||||
let _provider: UpdateProvider | undefined
|
let _provider: UpdateProvider | undefined
|
||||||
let _address: string | AddressInfo | null
|
|
||||||
const provider = (): UpdateProvider => {
|
const provider = (): UpdateProvider => {
|
||||||
if (!_provider) {
|
if (!_provider) {
|
||||||
throw new Error("Update provider has not been created")
|
throw new Error("Update provider has not been created")
|
||||||
|
@ -87,6 +86,7 @@ describe("update", () => {
|
||||||
return _provider
|
return _provider
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let address = new URL("http://localhost")
|
||||||
beforeAll(async () => {
|
beforeAll(async () => {
|
||||||
mockLogger()
|
mockLogger()
|
||||||
|
|
||||||
|
@ -105,12 +105,13 @@ describe("update", () => {
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
_address = server.address()
|
const addr = ensureAddress(server, "http")
|
||||||
if (!isAddressInfo(_address)) {
|
if (typeof addr === "string") {
|
||||||
throw new Error("unexpected address")
|
throw new Error("unable to run update tests with unix sockets")
|
||||||
}
|
}
|
||||||
|
address = addr
|
||||||
_provider = new UpdateProvider(`http://${_address?.address}:${_address?.port}/latest`, _settings)
|
address.pathname = "/latest"
|
||||||
|
_provider = new UpdateProvider(address.toString(), _settings)
|
||||||
})
|
})
|
||||||
|
|
||||||
afterAll(() => {
|
afterAll(() => {
|
||||||
|
@ -220,59 +221,51 @@ describe("update", () => {
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should reject if response has status code 500", async () => {
|
it("should reject if response has status code 500", async () => {
|
||||||
if (isAddressInfo(_address)) {
|
address.pathname = "/reject-status-code"
|
||||||
const mockURL = `http://${_address.address}:${_address.port}/reject-status-code`
|
const provider = new UpdateProvider(address.toString(), settings())
|
||||||
const provider = new UpdateProvider(mockURL, settings())
|
const update = await provider.getUpdate(true)
|
||||||
const update = await provider.getUpdate(true)
|
|
||||||
|
|
||||||
expect(update.version).toBe("unknown")
|
expect(update.version).toBe("unknown")
|
||||||
expect(logger.error).toHaveBeenCalled()
|
expect(logger.error).toHaveBeenCalled()
|
||||||
expect(logger.error).toHaveBeenCalledWith("Failed to get latest version", {
|
expect(logger.error).toHaveBeenCalledWith("Failed to get latest version", {
|
||||||
identifier: "error",
|
identifier: "error",
|
||||||
value: `${mockURL}: 500`,
|
value: `${address.toString()}: 500`,
|
||||||
})
|
})
|
||||||
}
|
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should reject if no location header provided", async () => {
|
it("should reject if no location header provided", async () => {
|
||||||
if (isAddressInfo(_address)) {
|
address.pathname = "/no-location-header"
|
||||||
const mockURL = `http://${_address.address}:${_address.port}/no-location-header`
|
const provider = new UpdateProvider(address.toString(), settings())
|
||||||
const provider = new UpdateProvider(mockURL, settings())
|
const update = await provider.getUpdate(true)
|
||||||
const update = await provider.getUpdate(true)
|
|
||||||
|
|
||||||
expect(update.version).toBe("unknown")
|
expect(update.version).toBe("unknown")
|
||||||
expect(logger.error).toHaveBeenCalled()
|
expect(logger.error).toHaveBeenCalled()
|
||||||
expect(logger.error).toHaveBeenCalledWith("Failed to get latest version", {
|
expect(logger.error).toHaveBeenCalledWith("Failed to get latest version", {
|
||||||
identifier: "error",
|
identifier: "error",
|
||||||
value: `received redirect with no location header`,
|
value: `received redirect with no location header`,
|
||||||
})
|
})
|
||||||
}
|
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should resolve the request with response.headers.location", async () => {
|
it("should resolve the request with response.headers.location", async () => {
|
||||||
version = "4.1.1"
|
version = "4.1.1"
|
||||||
if (isAddressInfo(_address)) {
|
address.pathname = "/with-location-header"
|
||||||
const mockURL = `http://${_address.address}:${_address.port}/with-location-header`
|
const provider = new UpdateProvider(address.toString(), settings())
|
||||||
const provider = new UpdateProvider(mockURL, settings())
|
const update = await provider.getUpdate(true)
|
||||||
const update = await provider.getUpdate(true)
|
|
||||||
|
|
||||||
expect(logger.error).not.toHaveBeenCalled()
|
expect(logger.error).not.toHaveBeenCalled()
|
||||||
expect(update.version).toBe("4.1.1")
|
expect(update.version).toBe("4.1.1")
|
||||||
}
|
|
||||||
})
|
})
|
||||||
|
|
||||||
it("should reject if more than 10 redirects", async () => {
|
it("should reject if more than 10 redirects", async () => {
|
||||||
if (isAddressInfo(_address)) {
|
address.pathname = "/redirect/11"
|
||||||
const mockURL = `http://${_address.address}:${_address.port}/redirect/11`
|
const provider = new UpdateProvider(address.toString(), settings())
|
||||||
const provider = new UpdateProvider(mockURL, settings())
|
const update = await provider.getUpdate(true)
|
||||||
const update = await provider.getUpdate(true)
|
|
||||||
|
|
||||||
expect(update.version).toBe("unknown")
|
expect(update.version).toBe("unknown")
|
||||||
expect(logger.error).toHaveBeenCalled()
|
expect(logger.error).toHaveBeenCalled()
|
||||||
expect(logger.error).toHaveBeenCalledWith("Failed to get latest version", {
|
expect(logger.error).toHaveBeenCalledWith("Failed to get latest version", {
|
||||||
identifier: "error",
|
identifier: "error",
|
||||||
value: `reached max redirects`,
|
value: `reached max redirects`,
|
||||||
})
|
})
|
||||||
}
|
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
|
@ -108,20 +108,6 @@ export function idleTimer(message: string, reject: (error: Error) => void, delay
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* A helper function which returns a boolean indicating whether
|
|
||||||
* the given address is AddressInfo and has .address
|
|
||||||
* and a .port property.
|
|
||||||
*/
|
|
||||||
export function isAddressInfo(address: unknown): address is net.AddressInfo {
|
|
||||||
return (
|
|
||||||
address !== null &&
|
|
||||||
typeof address !== "string" &&
|
|
||||||
(address as net.AddressInfo).port !== undefined &&
|
|
||||||
(address as net.AddressInfo).address !== undefined
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* If using a proxy, return the address of the proxy.
|
* If using a proxy, return the address of the proxy.
|
||||||
*
|
*
|
||||||
|
|
|
@ -35,7 +35,7 @@ export class HttpServer {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
this.hs.on("error", reject)
|
this.hs.on("error", reject)
|
||||||
|
|
||||||
this.hs.listen(0, "localhost", () => {
|
this.hs.listen(0, "127.0.0.1", () => {
|
||||||
this.hs.off("error", reject)
|
this.hs.off("error", reject)
|
||||||
resolve()
|
resolve()
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue