Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
184 changes: 184 additions & 0 deletions eslint-suppressions.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,184 @@
{
"eslint.config.js": {
"import-x/no-anonymous-default-export": {
"count": 1
}
},
"examples/s3-update-example-cli/src/commands/hello.ts": {
"@typescript-eslint/no-shadow": {
"count": 1
},
"@typescript-eslint/no-unsafe-assignment": {
"count": 5
},
"@typescript-eslint/no-unsafe-call": {
"count": 6
},
"@typescript-eslint/no-unsafe-member-access": {
"count": 7
},
"@typescript-eslint/prefer-nullish-coalescing": {
"count": 1
},
"import-x/no-unresolved": {
"count": 1
}
},
"examples/s3-update-example-cli/src/index.ts": {
"import-x/no-unresolved": {
"count": 1
}
},
"src/commands/update.ts": {
"@typescript-eslint/prefer-nullish-coalescing": {
"count": 1
},
"unicorn/import-style": {
"count": 1
},
"unicorn/no-array-reverse": {
"count": 1
},
"unicorn/no-computed-property-existence-check": {
"count": 1
},
"unicorn/prefer-object-iterable-methods": {
"count": 1
}
},
"src/hooks/init.ts": {
"@typescript-eslint/no-shadow": {
"count": 3
},
"@typescript-eslint/strict-void-return": {
"count": 1
},
"unicorn/import-style": {
"count": 1
},
"unicorn/prefer-ternary": {
"count": 1
}
},
"src/tar.ts": {
"@typescript-eslint/no-confusing-void-expression": {
"count": 1
},
"@typescript-eslint/no-shadow": {
"count": 1
},
"@typescript-eslint/no-unsafe-argument": {
"count": 1
},
"@typescript-eslint/strict-void-return": {
"count": 1
},
"@typescript-eslint/switch-exhaustiveness-check": {
"count": 1
},
"unicorn/import-style": {
"count": 1
}
},
"src/update.ts": {
"@eslint-community/eslint-comments/require-description": {
"count": 1
},
"@typescript-eslint/no-floating-promises": {
"count": 1
},
"@typescript-eslint/no-unsafe-argument": {
"count": 5
},
"@typescript-eslint/no-unsafe-member-access": {
"count": 8
},
"@typescript-eslint/no-unsafe-return": {
"count": 2
},
"@typescript-eslint/prefer-nullish-coalescing": {
"count": 4
},
"@typescript-eslint/return-await": {
"count": 1
},
"@typescript-eslint/strict-void-return": {
"count": 1
},
"@typescript-eslint/use-unknown-in-catch-callback-variable": {
"count": 1
},
"preserve-caught-error": {
"count": 1
},
"require-unicode-regexp": {
"count": 1
},
"unicorn/consistent-boolean-name": {
"count": 3
},
"unicorn/consistent-class-member-order": {
"count": 1
},
"unicorn/import-style": {
"count": 1
},
"unicorn/operator-assignment": {
"count": 1
},
"unicorn/prefer-number-coercion": {
"count": 1
}
},
"src/util.ts": {
"unicorn/consistent-boolean-name": {
"count": 1
},
"unicorn/import-style": {
"count": 1
}
},
"test/integration/sf.integration.ts": {
"@typescript-eslint/no-unsafe-argument": {
"count": 2
},
"@typescript-eslint/no-unsafe-assignment": {
"count": 6
},
"@typescript-eslint/no-unsafe-call": {
"count": 3
},
"@typescript-eslint/no-unsafe-member-access": {
"count": 8
},
"require-unicode-regexp": {
"count": 1
},
"unicorn/import-style": {
"count": 1
},
"unicorn/prefer-hoisting-branch-code": {
"count": 1
}
},
"test/update.test.ts": {
"@typescript-eslint/prefer-nullish-coalescing": {
"count": 5
},
"@typescript-eslint/strict-void-return": {
"count": 3
},
"require-unicode-regexp": {
"count": 43
},
"unicorn/logical-assignment-operators": {
"count": 1
},
"unicorn/no-non-function-verb-prefix": {
"count": 1
},
"unicorn/no-return-array-push": {
"count": 3
}
}
}
1 change: 1 addition & 0 deletions examples/s3-update-example-cli/src/commands/hello.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ static examples = [
hello world from ./src/hello.ts!
`,
]

static flags = {
// flag with no value (-f, --force)
force: flags.boolean({char: 'f'}),
Expand Down
6 changes: 3 additions & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,8 @@
"@types/tar-fs": "^2.0.2",
"chai": "^4.5.0",
"commitlint": "^19",
"eslint": "^9.39.5",
"eslint-config-oclif": "^6.0.179",
"eslint": "^10.9.1",
"eslint-config-oclif": "^7.1.7",
"eslint-config-prettier": "^10.1.8",
"husky": "^9.1.7",
"lint-staged": "^15",
Expand All @@ -43,7 +43,7 @@
"sinon": "^18.0.1",
"strip-ansi": "^7.2.0",
"ts-node": "^10.9.2",
"typescript": "^5.7.3"
"typescript": "^6"
},
"engines": {
"node": ">=18.0.0"
Expand Down
4 changes: 3 additions & 1 deletion src/commands/update.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import select from '@inquirer/select'
import {Args, Command, Flags, Interfaces, ux} from '@oclif/core'
import {Args, Command, Flags, type Interfaces, ux} from '@oclif/core'
import {printTable} from '@oclif/table'
import {got} from 'got'
import {basename} from 'node:path'
Expand All @@ -11,6 +11,7 @@ export default class UpdateCommand extends Command {
static args = {
channel: Args.string({optional: true}),
}

static description = 'update the <%= config.bin %> CLI'
static examples = [
{
Expand All @@ -30,6 +31,7 @@ export default class UpdateCommand extends Command {
description: 'See available versions:',
},
]

static flags = {
autoupdate: Flags.boolean({hidden: true}),
available: Flags.boolean({
Expand Down
11 changes: 7 additions & 4 deletions src/hooks/init.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
import {Interfaces} from '@oclif/core'
import {type Interfaces} from '@oclif/core'
import makeDebug from 'debug'
import {spawn} from 'node:child_process'
import {existsSync} from 'node:fs'
import {mkdir, open, stat, unlink, writeFile} from 'node:fs/promises'
import {join} from 'node:path'

import {touch} from '../util.js'

const debug = makeDebug('cli:updater')

function timestamp(msg: string): string {
Expand Down Expand Up @@ -94,10 +95,12 @@ export const init: Interfaces.Hook<'init'> = async function (opts) {
detached: !config.windows,
env: autoupdateEnv,
stdio: ['ignore', stream, stream],
...(config.windows ? {shell: true} : {}),
...(config.windows && {shell: true}),
})
.on('error', (e: Error) => process.emitWarning(e))
.on('close', () => fd.close())
.on('error', (e: Error) => {
process.emitWarning(e)
})
.on('close', async () => fd.close())
.unref()

async function claimAutoupdate(markerPath: string): Promise<boolean> {
Expand Down
16 changes: 8 additions & 8 deletions src/tar.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import {existsSync} from 'node:fs'
import {rename, rm} from 'node:fs/promises'
import {join} from 'node:path'
import zlib from 'node:zlib'
import {Headers, extract as tarExtract} from 'tar-fs'
import {type Headers, extract as tarExtract} from 'tar-fs'

import {touch} from './util.js'

Expand All @@ -29,15 +29,15 @@ const ignore = (_name: string, header?: Headers) => {
}

async function extract(stream: NodeJS.ReadableStream, basename: string, output: string, sha?: string): Promise<void> {
const getTmp = () => `${output}.partial.${Math.random().toString().split('.')[1].slice(0, 5)}`
const getTmp = () => `${output}.partial.${Math.random().toString().split('.', 2)[1].slice(0, 5)}`
let tmp = getTmp()
if (existsSync(tmp)) tmp = getTmp()
debug(`extracting to ${tmp}`)
try {
await new Promise((resolve, reject) => {
let shaValidated = false
let extracted = false
const check = () => shaValidated && extracted && resolve(null)
let isShaValidated = false
let isExtracted = false
const check = () => isShaValidated && isExtracted && resolve(null)

if (sha) {
const hasher = crypto.createHash('sha256')
Expand All @@ -46,18 +46,18 @@ async function extract(stream: NodeJS.ReadableStream, basename: string, output:
stream.on('end', () => {
const shasum = hasher.digest('hex')
if (sha === shasum) {
shaValidated = true
isShaValidated = true
check()
} else {
reject(new Error(`SHA mismatch: expected ${shasum} to be ${sha}`))
}
})
} else shaValidated = true
} else isShaValidated = true

const extract = tarExtract(tmp, {ignore})
extract.on('error', reject)
extract.on('finish', () => {
extracted = true
isExtracted = true
check()
})

Expand Down
20 changes: 10 additions & 10 deletions src/update.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import {Config, Interfaces, ux} from '@oclif/core'
import {Config, type Interfaces, ux} from '@oclif/core'
import {green, yellow} from 'ansis'
import makeDebug from 'debug'
import fileSize from 'filesize'
import {got, HTTPError} from 'got'
import {existsSync, Stats} from 'node:fs'
import {existsSync, type Stats} from 'node:fs'
import {mkdir, readdir, readFile, rm, stat, symlink, utimes, writeFile} from 'node:fs/promises'
import {basename, dirname, join} from 'node:path'
import {ProxyAgent} from 'proxy-agent'
Expand Down Expand Up @@ -91,7 +91,7 @@
if (version) {
const localVersion = force ? null : await this.findLocalVersion(version)

if (alreadyOnVersion(current, localVersion || null)) {

Check failure on line 94 in src/update.ts

View workflow job for this annotation

GitHub Actions / linux-unit-tests / linux-unit-tests (24.19.0)

Argument of type 'string | null' is not assignable to parameter of type 'string | undefined'.

Check failure on line 94 in src/update.ts

View workflow job for this annotation

GitHub Actions / linux-unit-tests / linux-unit-tests (24.19.0)

Argument of type 'string | null' is not assignable to parameter of type 'string | undefined'.

Check failure on line 94 in src/update.ts

View workflow job for this annotation

GitHub Actions / linux-unit-tests / linux-unit-tests (24.19.0)

Argument of type 'string | null' is not assignable to parameter of type 'string | undefined'.

Check failure on line 94 in src/update.ts

View workflow job for this annotation

GitHub Actions / linux-unit-tests / linux-unit-tests (22)

Argument of type 'string | null' is not assignable to parameter of type 'string | undefined'.

Check failure on line 94 in src/update.ts

View workflow job for this annotation

GitHub Actions / linux-unit-tests / linux-unit-tests (22)

Argument of type 'string | null' is not assignable to parameter of type 'string | undefined'.

Check failure on line 94 in src/update.ts

View workflow job for this annotation

GitHub Actions / linux-unit-tests / linux-unit-tests (22)

Argument of type 'string | null' is not assignable to parameter of type 'string | undefined'.
ux.action.stop(this.config.scopedEnvVar('HIDE_UPDATED_MESSAGE') ? 'done' : `already on version ${current}`)
return
}
Expand Down Expand Up @@ -245,7 +245,7 @@
await Promise.all(
files
.filter((f) => isNotSpecial(f.path, this.config.version) && isOld(f.stat))
.map((f) => rm(f.path, {force: true, recursive: true})),
.map(async (f) => rm(f.path, {force: true, recursive: true})),
)
} catch (error: unknown) {
ux.warn(error as Error | string)
Expand Down Expand Up @@ -301,7 +301,7 @@
}
}

const alreadyOnVersion = (current: string, updated: null | string): boolean => current === updated
const alreadyOnVersion = (current: string, updated: string | undefined): boolean => current === updated

const ensureClientDir = async (clientRoot: string): Promise<void> => {
try {
Expand Down Expand Up @@ -339,7 +339,7 @@

const composeS3SubDir = (config: Config): string => {
let s3SubDir = config.pjson.oclif.update?.s3?.folder || ''
if (s3SubDir !== '' && s3SubDir.slice(-1) !== '/') s3SubDir = `${s3SubDir}/`
if (s3SubDir !== '' && !s3SubDir.endsWith('/')) s3SubDir = `${s3SubDir}/`
return s3SubDir
}

Expand Down Expand Up @@ -399,10 +399,10 @@
const MAX_DEBOUNCE_WAIT_MS = 6 * 60 * 60 * 1000 // 6 hours
const DEBOUNCE_POLL_INTERVAL_MS = 60 * 1000 // 1 minute

const debounce = (cacheDir: string): Promise<void> => {
const debounce = async (cacheDir: string): Promise<void> => {
const lastrunfile = join(cacheDir, 'lastrun')
const startedAt = Date.now()
let announced = false
let isAnnounced = false

return new Promise((resolve) => {
const check = async (): Promise<void> => {
Expand All @@ -422,11 +422,11 @@
}

const msg = `waiting until ${m.toISOString()} to update`
if (announced) {
if (isAnnounced) {
debug(msg)
} else {
ux.stdout(msg)
announced = true
isAnnounced = true
}

setTimeout(check, DEBOUNCE_POLL_INTERVAL_MS)
Expand Down Expand Up @@ -532,7 +532,7 @@
const determineCurrentVersion = async (clientBin: string, version: string): Promise<string> => {
try {
const currentVersion = await readFile(clientBin, 'utf8')
const matches = currentVersion.match(/\.\.[/\\|](.+)[/\\|]bin/)
const matches = /\.\.[/\\|](.+)[/\\|]bin/.exec(currentVersion)
return matches ? matches[1] : version
} catch (error) {
if (error instanceof Error) {
Expand Down
Loading
Loading