-
Notifications
You must be signed in to change notification settings - Fork 42
Expand file tree
/
Copy pathcmd-patch-download.mts
More file actions
143 lines (122 loc) · 3.41 KB
/
cmd-patch-download.mts
File metadata and controls
143 lines (122 loc) · 3.41 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
import { existsSync } from 'node:fs'
import path from 'node:path'
import { DOT_SOCKET_DIR } from '@socketsecurity/lib/paths/dirnames'
import { getDefaultSpinner } from '@socketsecurity/lib/spinner'
import { handlePatchDownload } from './handle-patch-download.mts'
import { commonFlags, outputFlags } from '../../flags.mts'
import { meowOrExit } from '../../utils/cli/with-subcommands.mjs'
import { InputError } from '../../utils/error/errors.mjs'
import {
getFlagApiRequirementsOutput,
getFlagListOutput,
} from '../../utils/output/formatting.mts'
import { getOutputKind } from '../../utils/output/mode.mjs'
import { checkCommandInput } from '../../utils/validation/check-input.mts'
import type {
CliCommandConfig,
CliCommandContext,
CliSubcommand,
} from '../../utils/cli/with-subcommands.mjs'
export const CMD_NAME = 'download'
const description = 'Download patches from Socket API'
export const cmdPatchDownload: CliSubcommand = {
description,
hidden: false,
run,
}
async function run(
argv: string[] | readonly string[],
importMeta: ImportMeta,
{ parentName }: CliCommandContext,
): Promise<void> {
const config: CliCommandConfig = {
commandName: CMD_NAME,
description,
hidden: false,
flags: {
...commonFlags,
...outputFlags,
scan: {
type: 'string',
description: 'Download patches from scan results',
},
},
help: (command, config) => `
Usage
$ ${command} <uuid...>
$ ${command} --scan <scan-id>
API Token Requirements
${getFlagApiRequirementsOutput(`${parentName}:${CMD_NAME}`)}
Options
${getFlagListOutput(config.flags)}
Examples
$ ${command} 550e8400-e29b-41d4-a716-446655440000
$ ${command} uuid1 uuid2 uuid3
$ ${command} --scan scan-abc123
$ ${command} --scan scan-abc123 --json
`,
}
const cli = meowOrExit(
{
argv,
config,
parentName,
importMeta,
},
{ allowUnknownFlags: false },
)
const { json, markdown, scan } = cli.flags as unknown as {
json: boolean
markdown: boolean
scan?: string
}
const outputKind = getOutputKind(json, markdown)
const wasValidInput = checkCommandInput(outputKind, {
nook: true,
test: !json || !markdown,
message: 'The json and markdown flags cannot be both set, pick one',
fail: 'omit one',
})
if (!wasValidInput) {
return
}
let uuids: string[] = []
let cwd: string
if (scan) {
// When using --scan, we can use current directory
cwd = process.cwd()
} else {
if (cli.input.length === 0) {
throw new InputError('Must provide patch UUIDs or use --scan flag')
}
// First arg might be cwd if it's a directory
const firstArg = cli.input[0]
if (
firstArg &&
!firstArg.match(/^[0-9a-f-]{36}$/i) &&
existsSync(firstArg)
) {
cwd = firstArg
uuids = cli.input.slice(1) as string[]
} else {
cwd = process.cwd()
uuids = cli.input.slice() as string[]
}
}
cwd = path.resolve(cwd)
// Create .socket directory if it doesn't exist.
const dotSocketDirPath = path.join(cwd, DOT_SOCKET_DIR)
if (!existsSync(dotSocketDirPath)) {
throw new InputError(
`No ${DOT_SOCKET_DIR} directory found. Run 'socket scan create' first.`,
)
}
const spinner = getDefaultSpinner()
await handlePatchDownload({
cwd,
outputKind,
...(scan ? { scanId: scan } : {}),
spinner,
uuids,
})
}