@@ -324,7 +324,6 @@ func TestListInventoryPrefix(t *testing.T) {
324324 }
325325}
326326
327- // TODO -- FIXME: add test case(s) with empty invName
328327func TestListInventoryPrefixPermute (t * testing.T ) {
329328 tools .CheckSkip (t , & tools.SkipTestArgs {RemoteBck : true , Bck : cliBck })
330329
@@ -333,7 +332,7 @@ func TestListInventoryPrefixPermute(t *testing.T) {
333332 numA , numM , numZ int
334333 pageSize int64 // CreateNBIMsg.PageSize
335334 namesPerChunk int64
336- listPageSize int64 // listing PageSize
335+ listPageSize int64 // listing PageSize (best-effort for NBI)
337336 invName string
338337 }
339338 tests := []test {
@@ -343,6 +342,11 @@ func TestListInventoryPrefixPermute(t *testing.T) {
343342 pageSize : 3 , namesPerChunk : 6 , listPageSize : 4 ,
344343 invName : "inv-sc-sp" ,
345344 },
345+ {
346+ name : "small-chunks-pages-empty-invName" ,
347+ numA : 40 , numM : 30 , numZ : 50 ,
348+ pageSize : 3 , namesPerChunk : 6 , listPageSize : 4 ,
349+ },
346350 {
347351 name : "small-chunks-large-pages" ,
348352 numA : 40 , numM : 30 , numZ : 50 ,
@@ -361,6 +365,12 @@ func TestListInventoryPrefixPermute(t *testing.T) {
361365 pageSize : 10 , namesPerChunk : 8 , listPageSize : 5 ,
362366 invName : "inv-maxent" ,
363367 },
368+ {
369+ name : "zero-page-size" ,
370+ numA : 40 , numM : 30 , numZ : 50 ,
371+ pageSize : 3 , namesPerChunk : 6 , listPageSize : 0 ,
372+ invName : "inv-zero-ps" ,
373+ },
364374 }
365375
366376 bck := cliBck
@@ -372,12 +382,10 @@ func TestListInventoryPrefixPermute(t *testing.T) {
372382 parent = "p-" + cos .GenTie () + "/"
373383 bp = tools .BaseAPIParams ()
374384 )
375- // One init/cleanup only
385+
376386 m0 := & ioContext {t : t , bck : bck , prefix : parent }
377387 m0 .init (true /*cleanup*/ )
378388
379- // Three disjoint subtrees under parent: a/, m/, z/
380- // Ensures: a/ < m/ < z/ in lexicographic order.
381389 ma := & ioContext {t : t , bck : bck , prefix : parent + "a/" }
382390 mm := & ioContext {t : t , bck : bck , prefix : parent + "m/" }
383391 mz := & ioContext {t : t , bck : bck , prefix : parent + "z/" }
@@ -386,12 +394,10 @@ func TestListInventoryPrefixPermute(t *testing.T) {
386394 mm .num = tc .numM
387395 mz .num = tc .numZ
388396
389- // Per your note: pass-through writes, no remotePuts/evicting.
390397 ma .puts ()
391398 mm .puts ()
392399 mz .puts ()
393400
394- // Create inventory covering the entire parent prefix
395401 createMsg := & apc.CreateNBIMsg {
396402 Name : tc .invName ,
397403 LsoMsg : apc.LsoMsg {
@@ -409,16 +415,16 @@ func TestListInventoryPrefixPermute(t *testing.T) {
409415 _ , err = api .WaitForXactionIC (bp , & wargs )
410416 tassert .CheckFatal (t , err )
411417
412- // Helper: list NBI with token-loop guard, strict order, and prefix check.
413- list := func (prefix string , tc * test , invName string ) (entries []* cmn.LsoEnt ) {
418+ var args api.ListArgs
419+ if createMsg .Name != "" {
420+ args .Header = http.Header {apc .HdrInvName : []string {createMsg .Name }}
421+ }
422+
423+ listNBI := func (prefix string ) (entries []* cmn.LsoEnt ) {
414424 var (
415425 token string
416426 seenTok = make (cos.StrSet , 16 )
417- args api.ListArgs
418427 )
419- if invName != "" {
420- args .Header = http.Header {apc .HdrInvName : []string {invName }}
421- }
422428 for {
423429 lsmsg := & apc.LsoMsg {
424430 Prefix : prefix ,
@@ -427,14 +433,11 @@ func TestListInventoryPrefixPermute(t *testing.T) {
427433 Flags : apc .LsNBI ,
428434 ContinuationToken : token ,
429435 }
430- lst , err := api .ListObjects (bp , bck , lsmsg , args )
436+ lst , err := api .ListObjectsPage (bp , bck , lsmsg , args )
431437 tassert .CheckFatal (t , err )
432438
433- // page size sanity
434- if lst .ContinuationToken != "" {
435- tassert .Fatalf (t , len (lst .Entries ) <= int (tc .listPageSize ),
436- "page too large: got %d, max %d" , len (lst .Entries ), tc .listPageSize )
437- }
439+ tassert .Fatalf (t , len (lst .Entries ) > 0 || lst .ContinuationToken == "" ,
440+ "empty page with continuation token %q for prefix %q" , lst .ContinuationToken , prefix )
438441
439442 entries = append (entries , lst .Entries ... )
440443 if lst .ContinuationToken == "" {
@@ -445,7 +448,7 @@ func TestListInventoryPrefixPermute(t *testing.T) {
445448 seenTok .Set (lst .ContinuationToken )
446449 token = lst .ContinuationToken
447450 }
448- // strict order + prefix match
451+
449452 for i := range entries {
450453 tassert .Fatalf (t , strings .HasPrefix (entries [i ].Name , prefix ),
451454 "entry %q doesn't match prefix %q" , entries [i ].Name , prefix )
@@ -458,29 +461,31 @@ func TestListInventoryPrefixPermute(t *testing.T) {
458461 return entries
459462 }
460463
461- // 1) list sub-prefix in the middle => exercises: skip a/ chunks + Search in-chunk + stop before z/
462- gotM := list (mm .prefix , & tc , createMsg .Name )
463-
464- // validate set equality with PUT names
465- gotSet := make (cos.StrSet , len (gotM ))
466- for _ , e := range gotM {
467- gotSet .Set (e .Name )
468- }
469- var missed = make ([]string , 0 , 4 )
470- for _ , name := range mm .objNames {
471- if _ , ok := gotSet [name ]; ! ok {
472- missed = append (missed , name )
464+ missingFromEntries := func (expected []string , got []* cmn.LsoEnt ) []string {
465+ gotSet := make (cos.StrSet , len (got ))
466+ for _ , e := range got {
467+ gotSet .Set (e .Name )
473468 }
469+ missed := make ([]string , 0 , 4 )
470+ for _ , name := range expected {
471+ if _ , ok := gotSet [name ]; ! ok {
472+ missed = append (missed , name )
473+ }
474+ }
475+ return missed
474476 }
475- tassert .Fatalf (t , len (missed ) == 0 , "missing %v for prefix %q - %d out of %d expected" , missed , mm .prefix , len (missed ), len (mm .objNames ))
476- tassert .Fatalf (t , len (gotM ) == mm .num , "prefix %q: expected %d, got %d" , mm .prefix , mm .num , len (gotM ))
477477
478- // 2) list parent => must include all
479- gotParent := list (parent , & tc , createMsg .Name )
478+ gotM := listNBI (mm .prefix )
479+ missed := missingFromEntries (mm .objNames , gotM )
480+ tassert .Fatalf (t , len (missed ) == 0 ,
481+ "missing %v for prefix %q - %d out of %d expected" ,
482+ missed , mm .prefix , len (missed ), len (mm .objNames ))
483+ tassert .Fatalf (t , len (gotM ) == mm .num ,
484+ "prefix %q: expected %d, got %d" , mm .prefix , mm .num , len (gotM ))
485+
486+ gotParent := listNBI (parent )
480487 expTotal := ma .num + mm .num + mz .num
481488
482- clear (missed )
483- missed = missed [:0 ]
484489 expSet := make (cos.StrSet , expTotal )
485490 expSet .Add (ma .objNames ... )
486491 expSet .Add (mm .objNames ... )
@@ -491,18 +496,22 @@ func TestListInventoryPrefixPermute(t *testing.T) {
491496 for _ , en := range gotParent {
492497 gotParentSet .Set (en .Name )
493498 }
499+ missed = missed [:0 ]
494500 for name := range expSet {
495501 if _ , ok := gotParentSet [name ]; ! ok {
496502 missed = append (missed , name )
497503 }
498504 }
499- tassert .Fatalf (t , len (missed ) == 0 , "missing %v for parent prefix %q - %d out of %d expected" , missed , parent , len (missed ), expTotal )
500- tassert .Fatalf (t , len (gotParent ) == expTotal , "parent prefix %q: expected %d, got %d" , parent , expTotal , len (gotParent ))
505+ tassert .Fatalf (t , len (missed ) == 0 ,
506+ "missing %v for parent prefix %q - %d out of %d expected" ,
507+ missed , parent , len (missed ), expTotal )
508+ tassert .Fatalf (t , len (gotParent ) == expTotal ,
509+ "parent prefix %q: expected %d, got %d" , parent , expTotal , len (gotParent ))
501510
502- // 3) list missing prefix => must be empty (and must not loop tokens)
503511 missing := parent + "zzzz/"
504- gotMissing := list (missing , & tc , createMsg .Name )
505- tassert .Fatalf (t , len (gotMissing ) == 0 , "prefix %q: expected 0, got %d" , missing , len (gotMissing ))
512+ gotMissing := listNBI (missing )
513+ tassert .Fatalf (t , len (gotMissing ) == 0 ,
514+ "prefix %q: expected 0, got %d" , missing , len (gotMissing ))
506515 })
507516 }
508517}
0 commit comments