Skip to content

Commit ff94de3

Browse files
committed
Refuse an --include-dir on another Windows drive
Gathered files are stored relative to the app directory, and no relative path reaches another drive or a network share, so those files were silently left unscanned.
1 parent c261c47 commit ff94de3

2 files changed

Lines changed: 25 additions & 1 deletion

File tree

‎packages/app/src/cli/services/app-security-selection.test.ts‎

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -615,4 +615,20 @@ describe('mergeScanDirectories', () => {
615615
test('keeps a directory whose name only starts like another directory', () => {
616616
expect(mergeScanDirectories('/work/app', ['/work/app-library']).scanDirectories).toHaveLength(2)
617617
})
618+
619+
test('rejects an include directory on another Windows drive', () => {
620+
expect(() => mergeScanDirectories('C:/work/app', ['C:/work/backend', 'D:/backend'])).toThrowError(
621+
new AbortError('--include-dir D:/backend: must be on the same drive as the app directory.'),
622+
)
623+
})
624+
625+
test('rejects an include directory on a Windows network share', () => {
626+
expect(() => mergeScanDirectories('C:/work/app', ['//server/share/backend'])).toThrowError(
627+
new AbortError('--include-dir //server/share/backend: must be on the same drive as the app directory.'),
628+
)
629+
})
630+
631+
test('accepts an include directory elsewhere on the same Windows drive', () => {
632+
expect(mergeScanDirectories('C:/work/app', ['C:/backend']).scanDirectories).toHaveLength(2)
633+
})
618634
})

‎packages/app/src/cli/services/app-security-selection.ts‎

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ import {fetchOrCreateOrganizationApp} from './context.js'
44
import {NoAppConfigurationFoundError} from '../models/project/project.js'
55
import {AbortError} from '@shopify/cli-kit/node/error'
66
import {fileRealPath, isDirectory} from '@shopify/cli-kit/node/fs'
7-
import {basename, cwd, isSubpath, joinPath, resolvePath} from '@shopify/cli-kit/node/path'
7+
import {basename, cwd, isSubpath, joinPath, normalizePath, relativePath, resolvePath} from '@shopify/cli-kit/node/path'
88
import {renderConfirmationPrompt} from '@shopify/cli-kit/node/ui'
99

1010
export type AppSecuritySelection =
@@ -172,11 +172,19 @@ export async function resolveIncludeDirectories(includeDirs: ReadonlyArray<strin
172172
* because walking the outer one covers it; that includes the app directory when an include directory contains it.
173173
* `requestedScanDirectories` keeps the directories that were dropped for being nested, since each still gets the
174174
* ignored-scan-directory warning.
175+
*
176+
* Aborts on an include directory on another Windows drive or network share. Gathered files are stored relative to the
177+
* app directory and read back with `joinPath`, which can't reach those, so their files would be silently left unscanned.
175178
*/
176179
export function mergeScanDirectories(
177180
appDirectory: string,
178181
includeDirectories: ReadonlyArray<string>,
179182
): {scanDirectories: AppSecurityScanDirectory[]; requestedScanDirectories: string[]} {
183+
const otherDrive = includeDirectories.find(
184+
(directory) => joinPath(appDirectory, relativePath(appDirectory, directory)) !== normalizePath(directory),
185+
)
186+
if (otherDrive) throw new AbortError(`--include-dir ${otherDrive}: must be on the same drive as the app directory.`)
187+
180188
const requested = [
181189
{directory: appDirectory, origin: 'app_directory' as const},
182190
...includeDirectories.map((directory) => ({directory, origin: 'include_dir' as const})),

0 commit comments

Comments
 (0)