github.com/tiagovtristao/plz@v13.4.0+incompatible/src/cache/dir_cache_test.go (about)

     1  package cache
     2  
     3  import (
     4  	"bytes"
     5  	"encoding/base64"
     6  	"io/ioutil"
     7  	"os"
     8  	"path"
     9  	"testing"
    10  
    11  	"github.com/stretchr/testify/assert"
    12  
    13  	"github.com/thought-machine/please/src/core"
    14  )
    15  
    16  var hash = []byte("12345678901234567890")
    17  var b64Hash = base64.URLEncoding.EncodeToString(hash)
    18  
    19  func writeFile(filename string, size int) {
    20  	contents := bytes.Repeat([]byte{'p', 'l', 'z'}, size) // so this is three times the size...
    21  	if err := os.MkdirAll(path.Dir(filename), core.DirPermissions); err != nil {
    22  		panic(err)
    23  	}
    24  	if err := ioutil.WriteFile(filename, contents, 0644); err != nil {
    25  		panic(err)
    26  	}
    27  }
    28  
    29  func cachePath(target *core.BuildTarget, compress bool) string {
    30  	if compress {
    31  		return path.Join(".plz-cache-"+target.Label.PackageName, target.Label.PackageName, target.Label.Name, b64Hash+".tar.gz")
    32  	}
    33  	return path.Join(".plz-cache-"+target.Label.PackageName, target.Label.PackageName, target.Label.Name, b64Hash, target.Outputs()[0])
    34  }
    35  
    36  func inCache(target *core.BuildTarget) bool {
    37  	dest := cachePath(target, false)
    38  	log.Debug("Checking for %s", dest)
    39  	return core.PathExists(dest)
    40  }
    41  
    42  func inCompressedCache(target *core.BuildTarget) bool {
    43  	dest := cachePath(target, true)
    44  	log.Debug("Checking for %s", dest)
    45  	return core.PathExists(dest)
    46  }
    47  
    48  func TestStoreAndRetrieve(t *testing.T) {
    49  	cache := makeCache(".plz-cache-test1", false)
    50  	target := makeTarget("//test1:target1", 20)
    51  	cache.Store(target, hash)
    52  	// Should now exist in cache at this path
    53  	assert.True(t, inCache(target))
    54  	assert.True(t, cache.Retrieve(target, hash))
    55  	// Should be able to store it again without problems
    56  	cache.Store(target, hash)
    57  	assert.True(t, inCache(target))
    58  	assert.True(t, cache.Retrieve(target, hash))
    59  }
    60  
    61  func TestCleanNoop(t *testing.T) {
    62  	cache := makeCache(".plz-cache-test2", false)
    63  	target1 := makeTarget("//test2:target1", 2000)
    64  	cache.Store(target1, hash)
    65  	assert.True(t, inCache(target1))
    66  	target2 := makeTarget("//test2:target2", 2000)
    67  	cache.Store(target2, hash)
    68  	assert.True(t, inCache(target2))
    69  	// Doesn't clean anything this time because the high water mark is sufficiently high
    70  	totalSize := cache.clean(20000, 1000)
    71  	assert.EqualValues(t, 12000, totalSize)
    72  	assert.True(t, inCache(target1))
    73  	assert.True(t, inCache(target2))
    74  }
    75  
    76  func TestCleanNoop2(t *testing.T) {
    77  	cache := makeCache(".plz-cache-test3", false)
    78  	target1 := makeTarget("//test3:target1", 2000)
    79  	cache.Store(target1, hash)
    80  	assert.True(t, inCache(target1))
    81  	target2 := makeTarget("//test3:target2", 2000)
    82  	cache.Store(target2, hash)
    83  	assert.True(t, inCache(target2))
    84  	// Doesn't clean anything this time, the high water mark is lower but both targets have
    85  	// just been built.
    86  	totalSize := cache.clean(10000, 1000)
    87  	assert.EqualValues(t, 12000, totalSize)
    88  	assert.True(t, inCache(target1))
    89  	assert.True(t, inCache(target2))
    90  }
    91  
    92  func TestCleanForReal(t *testing.T) {
    93  	cache := makeCache(".plz-cache-test4", false)
    94  	target1 := makeTarget("//test4:target1", 2000)
    95  	cache.Store(target1, hash)
    96  	assert.True(t, inCache(target1))
    97  	target2 := makeTarget("//test4:target2", 2000)
    98  	writeFile(cachePath(target2, false), 2000)
    99  	assert.True(t, inCache(target2))
   100  	// This time it should clean target2, because target1 has just been stored
   101  	totalSize := cache.clean(10000, 1000)
   102  	assert.EqualValues(t, 6000, totalSize)
   103  	assert.True(t, inCache(target1))
   104  	assert.False(t, inCache(target2))
   105  }
   106  
   107  func TestCleanForReal2(t *testing.T) {
   108  	cache := makeCache(".plz-cache-test5", false)
   109  	target1 := makeTarget("//test5:target1", 2000)
   110  	writeFile(cachePath(target1, false), 2000)
   111  	assert.True(t, inCache(target1))
   112  	target2 := makeTarget("//test5:target2", 2000)
   113  	cache.Store(target2, hash)
   114  	assert.True(t, inCache(target2))
   115  	// This time it should clean target1, because target2 has just been stored
   116  	totalSize := cache.clean(10000, 1000)
   117  	assert.EqualValues(t, 6000, totalSize)
   118  	assert.False(t, inCache(target1))
   119  	assert.True(t, inCache(target2))
   120  }
   121  
   122  func TestStoreAndRetrieveCompressed(t *testing.T) {
   123  	cache := makeCache(".plz-cache-test6", true)
   124  	target := makeTarget("//test6:target6", 20)
   125  	cache.Store(target, hash)
   126  	// Should now exist in cache at this path
   127  	assert.True(t, inCompressedCache(target))
   128  	assert.True(t, cache.Retrieve(target, hash))
   129  	// Should be able to store it again without problems
   130  	cache.Store(target, hash)
   131  	assert.True(t, inCompressedCache(target))
   132  	assert.True(t, cache.Retrieve(target, hash))
   133  }
   134  
   135  func TestCleanCompressed(t *testing.T) {
   136  	cache := makeCache(".plz-cache-test7", true)
   137  	target1 := makeTarget("//test7:target1", 2000)
   138  	writeFile(cachePath(target1, true), 2000)
   139  	assert.True(t, inCompressedCache(target1))
   140  	target2 := makeTarget("//test7:target2", 2000)
   141  	cache.Store(target2, hash)
   142  	assert.True(t, inCompressedCache(target2))
   143  	// Don't want to assert the size here since it depends on how well gzip compresses.
   144  	// It's a bit hard to know exactly what the sizes here should be too but we'll guess
   145  	// and assume it won't change dramatically.
   146  	cache.clean(3000, 1000)
   147  	assert.False(t, inCompressedCache(target1))
   148  	assert.True(t, inCompressedCache(target2))
   149  }
   150  
   151  func makeCache(dir string, compress bool) *dirCache {
   152  	config := core.DefaultConfiguration()
   153  	config.Cache.Dir = dir
   154  	config.Cache.DirClean = false // We will do this explicitly
   155  	config.Cache.DirCompress = compress
   156  	return newDirCache(config)
   157  }
   158  
   159  func makeTarget(label string, size int) *core.BuildTarget {
   160  	target := core.NewBuildTarget(core.ParseBuildLabel(label, ""))
   161  	target.AddOutput("test.go")
   162  	writeFile(path.Join("plz-out/gen", target.Label.PackageName, "test.go"), size)
   163  	return target
   164  }