@@ -109,7 +109,7 @@ func TestExecuteContainerScan_Success(t *testing.T) {
109109 pkgTypesFlag = ""
110110 ignoreUnfixedFlag = true
111111
112- exitCode := executeContainerScan ([] string { "alpine:latest" } )
112+ exitCode := executeContainerScan ("alpine:latest" )
113113 assert .Equal (t , 0 , exitCode )
114114 assert .Len (t , mockRunner .Calls , 1 )
115115 assert .Equal (t , "/usr/local/bin/trivy" , mockRunner .Calls [0 ].Name )
@@ -149,46 +149,16 @@ func TestExecuteContainerScan_VulnerabilitiesFound(t *testing.T) {
149149 pkgTypesFlag = ""
150150 ignoreUnfixedFlag = true
151151
152- exitCode := executeContainerScan ([] string { "alpine:latest" } )
152+ exitCode := executeContainerScan ("alpine:latest" )
153153 assert .Equal (t , 1 , exitCode , "Should return exit code 1 when vulnerabilities are found" )
154154 assert .Len (t , mockRunner .Calls , 1 )
155155}
156156
157- func TestExecuteContainerScan_MultipleImages_SomeWithVulnerabilities (t * testing.T ) {
158- state := saveState ()
159- defer state .restore ()
160-
161- getTrivyPathResolver = func () (string , error ) {
162- return "/usr/local/bin/trivy" , nil
163- }
164-
165- callCount := 0
166- mockRunner := & MockCommandRunner {
167- RunFunc : func (_ string , _ []string ) error {
168- callCount ++
169- // Second image has vulnerabilities
170- if callCount == 2 {
171- return & mockExitError {code : 1 }
172- }
173- return nil
174- },
175- }
176- commandRunner = mockRunner
177-
178- severityFlag = ""
179- pkgTypesFlag = ""
180- ignoreUnfixedFlag = true
181-
182- exitCode := executeContainerScan ([]string {"alpine:latest" , "nginx:latest" , "redis:7" })
183- assert .Equal (t , 1 , exitCode , "Should return exit code 1 when any image has vulnerabilities" )
184- assert .Len (t , mockRunner .Calls , 3 , "Should scan all images even if one has vulnerabilities" )
185- }
186-
187157func TestExecuteContainerScan_InvalidImageName (t * testing.T ) {
188158 state := saveState ()
189159 defer state .restore ()
190160
191- exitCode := executeContainerScan ([] string { "nginx;rm -rf /" } )
161+ exitCode := executeContainerScan ("nginx;rm -rf /" )
192162 assert .Equal (t , 2 , exitCode )
193163}
194164
@@ -206,45 +176,12 @@ func TestExecuteContainerScan_TrivyNotFound(t *testing.T) {
206176 capturedExitCode = code
207177 }
208178
209- exitCode := executeContainerScan ([] string { "alpine:latest" } )
179+ exitCode := executeContainerScan ("alpine:latest" )
210180 // handleTrivyNotFound calls exitFunc(2), then returns 2
211181 assert .Equal (t , 2 , capturedExitCode )
212182 assert .Equal (t , 2 , exitCode )
213183}
214184
215- func TestExecuteContainerScan_MultipleImages_AllPass (t * testing.T ) {
216- state := saveState ()
217- defer state .restore ()
218-
219- getTrivyPathResolver = func () (string , error ) {
220- return "/usr/local/bin/trivy" , nil
221- }
222-
223- mockRunner := & MockCommandRunner {
224- RunFunc : func (_ string , _ []string ) error {
225- return nil
226- },
227- }
228- commandRunner = mockRunner
229-
230- severityFlag = ""
231- pkgTypesFlag = ""
232- ignoreUnfixedFlag = true
233-
234- exitCode := executeContainerScan ([]string {"alpine:latest" , "nginx:latest" , "redis:7" })
235- assert .Equal (t , 0 , exitCode )
236- assert .Len (t , mockRunner .Calls , 3 )
237- }
238-
239- func TestExecuteContainerScan_MultipleImages_OneInvalid (t * testing.T ) {
240- state := saveState ()
241- defer state .restore ()
242-
243- // Should fail validation before running any scans
244- exitCode := executeContainerScan ([]string {"alpine:latest" , "nginx;bad" , "redis:7" })
245- assert .Equal (t , 2 , exitCode )
246- }
247-
248185func TestExecuteContainerScan_TrivyExecutionError (t * testing.T ) {
249186 state := saveState ()
250187 defer state .restore ()
@@ -265,27 +202,10 @@ func TestExecuteContainerScan_TrivyExecutionError(t *testing.T) {
265202 pkgTypesFlag = ""
266203 ignoreUnfixedFlag = true
267204
268- exitCode := executeContainerScan ([] string { "alpine:latest" } )
205+ exitCode := executeContainerScan ("alpine:latest" )
269206 assert .Equal (t , 2 , exitCode )
270207}
271208
272- func TestExecuteContainerScan_EmptyImageList (t * testing.T ) {
273- state := saveState ()
274- defer state .restore ()
275-
276- getTrivyPathResolver = func () (string , error ) {
277- return "/usr/local/bin/trivy" , nil
278- }
279-
280- mockRunner := & MockCommandRunner {}
281- commandRunner = mockRunner
282-
283- // Empty list should succeed with no scans performed
284- exitCode := executeContainerScan ([]string {})
285- assert .Equal (t , 0 , exitCode )
286- assert .Len (t , mockRunner .Calls , 0 )
287- }
288-
289209// Tests for handleTrivyNotFound
290210
291211func TestHandleTrivyNotFound (t * testing.T ) {
@@ -448,7 +368,7 @@ func TestContainerScanCommandSkipsValidation(t *testing.T) {
448368}
449369
450370func TestContainerScanCommandRequiresArg (t * testing.T ) {
451- assert .Equal (t , "container-scan <IMAGE_NAME> [IMAGE_NAME...] " , containerScanCmd .Use , "Command use should match expected format" )
371+ assert .Equal (t , "container-scan <IMAGE_NAME>" , containerScanCmd .Use , "Command use should match expected format" )
452372
453373 err := containerScanCmd .Args (containerScanCmd , []string {})
454374 assert .Error (t , err , "Should error when no args provided" )
@@ -457,10 +377,7 @@ func TestContainerScanCommandRequiresArg(t *testing.T) {
457377 assert .NoError (t , err , "Should not error when one arg provided" )
458378
459379 err = containerScanCmd .Args (containerScanCmd , []string {"image1" , "image2" })
460- assert .NoError (t , err , "Should not error when multiple args provided" )
461-
462- err = containerScanCmd .Args (containerScanCmd , []string {"image1" , "image2" , "image3" })
463- assert .NoError (t , err , "Should not error when many args provided" )
380+ assert .Error (t , err , "Should error when multiple args provided" )
464381}
465382
466383func TestContainerScanFlagDefaults (t * testing.T ) {
@@ -551,80 +468,24 @@ func TestBuildTrivyArgsDefaultsApplied(t *testing.T) {
551468 assert .Contains (t , args , "--ignore-unfixed" , "--ignore-unfixed should be present when enabled" )
552469}
553470
554- // Tests for multiple image support
555-
556- func TestValidateMultipleImages (t * testing.T ) {
557- // All valid images should pass
558- validImages := []string {"alpine:latest" , "nginx:1.21" , "redis:7" }
559- for _ , img := range validImages {
560- err := validateImageName (img )
561- assert .NoError (t , err , "Valid image %s should not error" , img )
562- }
563- }
564-
565- func TestValidateMultipleImagesFailsOnInvalid (t * testing.T ) {
566- // Test that validation catches invalid images in a list
567- images := []string {"alpine:latest" , "nginx;malicious" , "redis:7" }
568-
569- var firstError error
570- for _ , img := range images {
571- if err := validateImageName (img ); err != nil {
572- firstError = err
573- break
574- }
575- }
576-
577- assert .Error (t , firstError , "Should catch invalid image in list" )
578- assert .Contains (t , firstError .Error (), "disallowed character" , "Should report specific error" )
579- }
580-
581- func TestBuildTrivyArgsForMultipleImages (t * testing.T ) {
471+ func TestBuildTrivyArgsWithDifferentImages (t * testing.T ) {
582472 severityFlag = "CRITICAL"
583473 pkgTypesFlag = ""
584474 ignoreUnfixedFlag = true
585475
586476 images := []string {"alpine:latest" , "nginx:1.21" , "redis:7" }
587477
588- // Verify each image gets correct args with same flags
589478 for _ , img := range images {
590479 args := buildTrivyArgs (img )
591-
592480 assert .Equal (t , img , args [len (args )- 1 ], "Image name should be last argument" )
593481 assert .Contains (t , args , "--severity" , "Should contain severity flag" )
594482 assert .Contains (t , args , "CRITICAL" , "Should use configured severity" )
595483 }
596484}
597485
598- func TestContainerScanCommandAcceptsMultipleImages (t * testing.T ) {
599- tests := []struct {
600- name string
601- args []string
602- errMsg string
603- }{
604- {
605- name : "single image" ,
606- args : []string {"alpine:latest" },
607- },
608- {
609- name : "two images" ,
610- args : []string {"alpine:latest" , "nginx:1.21" },
611- },
612- {
613- name : "three images" ,
614- args : []string {"alpine:latest" , "nginx:1.21" , "redis:7" },
615- },
616- {
617- name : "many images" ,
618- args : []string {"img1:v1" , "img2:v2" , "img3:v3" , "img4:v4" , "img5:v5" },
619- },
620- }
621-
622- for _ , tt := range tests {
623- t .Run (tt .name , func (t * testing.T ) {
624- err := containerScanCmd .Args (containerScanCmd , tt .args )
625- assert .NoError (t , err , "Command should accept %d image(s)" , len (tt .args ))
626- })
627- }
486+ func TestContainerScanCommandAcceptsExactlyOneImage (t * testing.T ) {
487+ err := containerScanCmd .Args (containerScanCmd , []string {"alpine:latest" })
488+ assert .NoError (t , err , "Command should accept single image" )
628489}
629490
630491func TestContainerScanCommandRejectsNoImages (t * testing.T ) {
0 commit comments