@@ -197,12 +197,12 @@ export function makeSubmitCommand(): Command {
197197 throw new CliError ( `No local file found for upload instruction: ${ instruction . filename } ` ) ;
198198 }
199199 const filePath = attachmentArgs . find ( arg =>
200- ! arg . startsWith ( 'http' ) && path . basename ( path . resolve ( arg ) ) === instruction . filename ,
200+ ! arg . startsWith ( 'http' ) && path . basename ( safeResolvePath ( arg ) ) === instruction . filename ,
201201 ) ;
202202 if ( ! filePath ) {
203203 throw new CliError ( `Cannot locate local file for presigned upload: ${ instruction . filename } ` ) ;
204204 }
205- await uploadViaPresignedPost ( path . resolve ( filePath ) , instruction ) ;
205+ await uploadViaPresignedPost ( safeResolvePath ( filePath ) , instruction ) ;
206206 process . stderr . write ( ` Uploaded: ${ instruction . filename } \n` ) ;
207207 }
208208
@@ -227,6 +227,19 @@ export function makeSubmitCommand(): Command {
227227// Attachment resolution helpers
228228// ---------------------------------------------------------------------------
229229
230+ /** Resolve a user-supplied path and validate it stays under CWD (CWE-22 mitigation). */
231+ function safeResolvePath ( userPath : string ) : string {
232+ // nosemgrep: path-join-resolve-traversal -- this IS the path-traversal guard
233+ const resolved = path . resolve ( userPath ) ;
234+ const cwd = process . cwd ( ) ;
235+ if ( ! resolved . startsWith ( cwd + path . sep ) && resolved !== cwd ) {
236+ throw new CliError (
237+ `Attachment path must be within the working directory: ${ userPath } ` ,
238+ ) ;
239+ }
240+ return resolved ;
241+ }
242+
230243const MAX_INLINE_SIZE_BYTES = 500 * 1024 ; // 500 KB
231244
232245/** MIME type lookup by file extension. */
@@ -263,7 +276,7 @@ function resolveAttachmentArg(arg: string): Attachment {
263276 }
264277
265278 // Local file
266- const resolvedPath = path . resolve ( arg ) ;
279+ const resolvedPath = safeResolvePath ( arg ) ;
267280 if ( ! fs . existsSync ( resolvedPath ) ) {
268281 throw new CliError ( `Attachment file not found: ${ arg } ` ) ;
269282 }
0 commit comments