@@ -1400,6 +1400,84 @@ func TestPersistence(t *testing.T) {
14001400 require .Equal (t , dgstFileData0 , dgst )
14011401}
14021402
1403+ func TestChecksumUpdateDirectory (t * testing.T ) {
1404+ t .Parallel ()
1405+ tmpdir := t .TempDir ()
1406+
1407+ snapshotter , err := native .NewSnapshotter (filepath .Join (tmpdir , "snapshots" ))
1408+ require .NoError (t , err )
1409+ t .Cleanup (func () {
1410+ require .NoError (t , snapshotter .Close ())
1411+ })
1412+
1413+ cm , cleanup := setupCacheManager (t , tmpdir , "native" , snapshotter )
1414+ t .Cleanup (cleanup )
1415+
1416+ ch := []string {
1417+ "ADD d0 dir" ,
1418+ "ADD d0/foo dir" ,
1419+ "ADD d0/foo/bar file data0" ,
1420+ "ADD d0/foo/subdir1 dir" ,
1421+ "ADD d0/foo/subdir1/baz file data1" ,
1422+ "ADD d0/foo/subdir2 dir" ,
1423+ }
1424+
1425+ ref := createRef (t , cm , nil )
1426+
1427+ cc , err := newCacheContext (ref )
1428+ require .NoError (t , err )
1429+
1430+ err = emit (cc .HandleChange , changeStream (ch ))
1431+ require .NoError (t , err )
1432+
1433+ fooDgst1 , err := cc .Checksum (context .TODO (), ref , "d0/foo" , ChecksumOpts {}, nil )
1434+ require .NoError (t , err )
1435+ require .Equal (t , digest .Digest ("sha256:e76717544f71725bd759a981554ca17c286b3d222598f46a671b983fd2b8172d" ), fooDgst1 )
1436+
1437+ barDgst1 , err := cc .Checksum (context .TODO (), ref , "d0/foo/bar" , ChecksumOpts {}, nil )
1438+ require .NoError (t , err )
1439+ require .Equal (t , digest .Digest ("sha256:cd8e75bca50f2d695f220d0cb0997d8ead387e4f926e8669a92d7f104cc9885b" ), barDgst1 )
1440+
1441+ // change d0/foo's permissions
1442+ updateFooCh := parseChange ("CHG d0/foo dir" )
1443+ fi , ok := updateFooCh .fi .(* fsutil.StatInfo )
1444+ require .True (t , ok )
1445+ prevMode := fi .Stat .Mode
1446+ fi .Stat .Mode = uint32 (os .ModeDir ) | 0700
1447+ require .NotEqual (t , prevMode , fi .Stat .Mode ) // sanity check we actually changed something
1448+
1449+ err = emit (cc .HandleChange , []* change {updateFooCh })
1450+ require .NoError (t , err )
1451+
1452+ // d0/foo should have a different digest now
1453+ fooDgst2 , err := cc .Checksum (context .TODO (), ref , "d0/foo" , ChecksumOpts {}, nil )
1454+ require .NoError (t , err )
1455+ require .NotEqual (t , fooDgst1 , fooDgst2 )
1456+ require .Equal (t , digest .Digest ("sha256:3a729f6ba0d3d74c6ade7d118b08b46e37e447afdad7fc6e258dbba12fa80141" ), fooDgst2 )
1457+
1458+ // but files under the dir should be the same as before
1459+ barDgst2 , err := cc .Checksum (context .TODO (), ref , "d0/foo/bar" , ChecksumOpts {}, nil )
1460+ require .NoError (t , err )
1461+ require .Equal (t , barDgst1 , barDgst2 )
1462+
1463+ // replace d0/foo with a file
1464+ err = emit (cc .HandleChange , changeStream ([]string {
1465+ "CHG d0/foo file data2" ,
1466+ }))
1467+ require .NoError (t , err )
1468+
1469+ // d0/foo should again have a different digest now
1470+ fooDgst3 , err := cc .Checksum (context .TODO (), ref , "d0/foo" , ChecksumOpts {}, nil )
1471+ require .NoError (t , err )
1472+ require .NotEqual (t , fooDgst1 , fooDgst3 )
1473+ require .NotEqual (t , fooDgst2 , fooDgst3 )
1474+ require .Equal (t , digest .Digest ("sha256:1c67653c3cf95b12a0014e2c4cd1d776b474b3218aee54155d6ae27b9b999c54" ), fooDgst3 )
1475+
1476+ // files under the old dir should not exist anymore
1477+ _ , err = cc .Checksum (context .TODO (), ref , "d0/foo/bar" , ChecksumOpts {}, nil )
1478+ require .ErrorContains (t , err , "not found" )
1479+ }
1480+
14031481func createRef (t * testing.T , cm cache.Manager , files []string ) cache.ImmutableRef {
14041482 if runtime .GOOS == "windows" && len (files ) > 0 {
14051483 // lm.Mount() will fail
0 commit comments