Skip to content

Commit 4df7688

Browse files
zkochanclaude
andcommitted
fix: address code review feedback
- Constrain pMapValues K generic to string (matches Object.entries behavior) - Remove unused writeJsonFile/loadJsonFile imports in rename-overwrite test - Properly handle URL cwd in safe-execa via fileURLToPath - Normalize args to mutable array instead of type-casting in safe-execa Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
1 parent 3cfec86 commit 4df7688

File tree

3 files changed

+18
-9
lines changed

3 files changed

+18
-9
lines changed

p-map-values/src/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
export async function pMapValues<K extends string | number | symbol, V, U> (
1+
export async function pMapValues<K extends string, V, U> (
22
mapper: (value: V, key: K, obj: Record<K, V>) => Promise<U>,
33
obj: Record<K, V>
44
): Promise<Record<K, U>> {

rename-overwrite/test.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,8 @@ import fs from 'node:fs'
22
import path from 'node:path'
33
import { test, describe } from 'node:test'
44
import assert from 'node:assert'
5-
import { writeJsonFile, writeJsonFileSync } from 'write-json-file'
6-
import { loadJsonFile, loadJsonFileSync } from 'load-json-file'
5+
import { writeJsonFileSync } from 'write-json-file'
6+
import { loadJsonFileSync } from 'load-json-file'
77
import { renameOverwrite, renameOverwriteSync } from 'rename-overwrite'
88
import symlinkDir from 'symlink-dir'
99
import { temporaryDirectory } from 'tempy'

safe-execa/src/index.ts

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { fileURLToPath } from 'node:url'
12
import which from '@zkochan/which'
23
import { execa, execaSync } from 'execa'
34
import type { Options, SyncOptions, ResultPromise, SyncResult } from 'execa'
@@ -7,22 +8,29 @@ export type { Options, SyncOptions, ResultPromise, SyncResult }
78

89
const pathCache = new Map<string, string | undefined>()
910

11+
function cwdToString (cwd: string | URL | undefined): string {
12+
if (cwd == null) return process.cwd()
13+
if (cwd instanceof URL) return fileURLToPath(cwd)
14+
return cwd
15+
}
16+
1017
export function sync (
1118
file: string,
1219
args?: readonly string[],
1320
options?: SyncOptions
1421
): SyncResult {
22+
const normalizedArgs = args ? [...args] : []
1523
try {
16-
which.sync(file, { path: options?.cwd as string ?? process.cwd() })
24+
which.sync(file, { path: cwdToString(options?.cwd) })
1725
} catch (err: any) {
1826
// If the command is not found in the current directory, there is no need to resolve the command to full location
1927
// as there is no danger of binary planting attack on Windows
2028
if (err.code === 'ENOENT') {
21-
return execaSync(file, args as string[], options)
29+
return execaSync(file, normalizedArgs, options)
2230
}
2331
}
2432
const fileAbsolutePath = getCommandAbsolutePathSync(file, options)
25-
return execaSync(fileAbsolutePath, args as string[], options)
33+
return execaSync(fileAbsolutePath, normalizedArgs, options)
2634
}
2735

2836
function getCommandAbsolutePathSync (file: string, options?: {
@@ -47,15 +55,16 @@ export function safeExeca (
4755
args?: readonly string[],
4856
options?: Options
4957
): ResultPromise {
58+
const normalizedArgs = args ? [...args] : []
5059
try {
51-
which.sync(file, { path: options?.cwd as string ?? process.cwd() })
60+
which.sync(file, { path: cwdToString(options?.cwd) })
5261
} catch (err: any) {
5362
// If the command is not found in the current directory, there is no need to resolve the command to full location
5463
// as there is no danger of binary planting attack on Windows
5564
if (err.code === 'ENOENT') {
56-
return execa(file, args as string[], options)
65+
return execa(file, normalizedArgs, options)
5766
}
5867
}
5968
const fileAbsolutePath = getCommandAbsolutePathSync(file, options)
60-
return execa(fileAbsolutePath, args as string[], options)
69+
return execa(fileAbsolutePath, normalizedArgs, options)
6170
}

0 commit comments

Comments
 (0)