github.com/docker/buildx@v0.14.1-0.20240514123050-afcb609966dc/store/store_test.go (about) 1 package store 2 3 import ( 4 "os" 5 "testing" 6 "time" 7 8 "github.com/pkg/errors" 9 "github.com/stretchr/testify/require" 10 ) 11 12 func TestEmptyStartup(t *testing.T) { 13 t.Parallel() 14 tmpdir, err := os.MkdirTemp("", "buildx-store") 15 require.NoError(t, err) 16 defer os.RemoveAll(tmpdir) 17 18 s, err := New(tmpdir) 19 require.NoError(t, err) 20 21 txn, release, err := s.Txn() 22 require.NoError(t, err) 23 defer release() 24 25 ng, err := txn.Current("foo") 26 require.NoError(t, err) 27 require.Nil(t, ng) 28 } 29 30 func TestNodeLocking(t *testing.T) { 31 t.Parallel() 32 tmpdir, err := os.MkdirTemp("", "buildx-store") 33 require.NoError(t, err) 34 defer os.RemoveAll(tmpdir) 35 36 s, err := New(tmpdir) 37 require.NoError(t, err) 38 39 _, release, err := s.Txn() 40 require.NoError(t, err) 41 42 ready := make(chan struct{}) 43 44 go func() { 45 _, release, err := s.Txn() 46 require.NoError(t, err) 47 release() 48 close(ready) 49 }() 50 51 select { 52 case <-time.After(100 * time.Millisecond): 53 case <-ready: 54 require.Fail(t, "transaction should have waited") 55 } 56 57 release() 58 select { 59 case <-time.After(200 * time.Millisecond): 60 require.Fail(t, "transaction should have completed") 61 case <-ready: 62 } 63 } 64 65 func TestNodeManagement(t *testing.T) { 66 t.Parallel() 67 tmpdir, err := os.MkdirTemp("", "buildx-store") 68 require.NoError(t, err) 69 defer os.RemoveAll(tmpdir) 70 71 s, err := New(tmpdir) 72 require.NoError(t, err) 73 74 txn, release, err := s.Txn() 75 require.NoError(t, err) 76 defer release() 77 78 err = txn.Save(&NodeGroup{ 79 Name: "foo/bar", 80 Driver: "driver", 81 }) 82 require.Error(t, err) 83 require.Contains(t, err.Error(), "invalid name") 84 85 err = txn.Save(&NodeGroup{ 86 Name: "mybuild", 87 Driver: "mydriver", 88 }) 89 require.NoError(t, err) 90 91 ng, err := txn.NodeGroupByName("mybuild") 92 require.NoError(t, err) 93 require.Equal(t, "mybuild", ng.Name) 94 require.Equal(t, "mydriver", ng.Driver) 95 require.True(t, !ng.LastActivity.IsZero()) 96 97 _, err = txn.NodeGroupByName("mybuild2") 98 require.Error(t, err) 99 require.True(t, os.IsNotExist(errors.Cause(err))) 100 101 err = txn.Save(&NodeGroup{ 102 Name: "mybuild2", 103 Driver: "mydriver2", 104 }) 105 require.NoError(t, err) 106 107 ng, err = txn.NodeGroupByName("mybuild2") 108 require.NoError(t, err) 109 require.Equal(t, "mybuild2", ng.Name) 110 require.Equal(t, "mydriver2", ng.Driver) 111 112 // update existing 113 err = txn.Save(&NodeGroup{ 114 Name: "mybuild", 115 Driver: "mydriver-mod", 116 }) 117 require.NoError(t, err) 118 119 ng, err = txn.NodeGroupByName("mybuild") 120 require.NoError(t, err) 121 require.Equal(t, "mybuild", ng.Name) 122 require.Equal(t, "mydriver-mod", ng.Driver) 123 124 ngs, err := txn.List() 125 require.NoError(t, err) 126 require.Equal(t, 2, len(ngs)) 127 128 // test setting current 129 err = txn.SetCurrent("foo", "mybuild", false, false) 130 require.NoError(t, err) 131 132 ng, err = txn.Current("foo") 133 require.NoError(t, err) 134 require.NotNil(t, ng) 135 require.Equal(t, "mybuild", ng.Name) 136 137 ng, err = txn.Current("foo") 138 require.NoError(t, err) 139 require.NotNil(t, ng) 140 require.Equal(t, "mybuild", ng.Name) 141 142 ng, err = txn.Current("bar") 143 require.NoError(t, err) 144 require.Nil(t, ng) 145 146 ng, err = txn.Current("foo") 147 require.NoError(t, err) 148 require.Nil(t, ng) 149 150 // set with default 151 err = txn.SetCurrent("foo", "mybuild", false, true) 152 require.NoError(t, err) 153 154 ng, err = txn.Current("foo") 155 require.NoError(t, err) 156 require.NotNil(t, ng) 157 require.Equal(t, "mybuild", ng.Name) 158 159 ng, err = txn.Current("bar") 160 require.NoError(t, err) 161 require.Nil(t, ng) 162 163 ng, err = txn.Current("foo") 164 require.NoError(t, err) 165 require.NotNil(t, ng) 166 require.Equal(t, "mybuild", ng.Name) 167 168 err = txn.SetCurrent("foo", "mybuild2", false, true) 169 require.NoError(t, err) 170 171 ng, err = txn.Current("foo") 172 require.NoError(t, err) 173 require.NotNil(t, ng) 174 require.Equal(t, "mybuild2", ng.Name) 175 176 err = txn.SetCurrent("bar", "mybuild", false, false) 177 require.NoError(t, err) 178 179 ng, err = txn.Current("bar") 180 require.NoError(t, err) 181 require.NotNil(t, ng) 182 require.Equal(t, "mybuild", ng.Name) 183 184 ng, err = txn.Current("foo") 185 require.NoError(t, err) 186 require.NotNil(t, ng) 187 require.Equal(t, "mybuild2", ng.Name) 188 189 // set global 190 err = txn.SetCurrent("foo", "mybuild2", true, false) 191 require.NoError(t, err) 192 193 ng, err = txn.Current("foo") 194 require.NoError(t, err) 195 require.NotNil(t, ng) 196 require.Equal(t, "mybuild2", ng.Name) 197 198 ng, err = txn.Current("bar") 199 require.NoError(t, err) 200 require.NotNil(t, ng) 201 require.Equal(t, "mybuild2", ng.Name) 202 203 err = txn.SetCurrent("bar", "mybuild", false, false) 204 require.NoError(t, err) 205 206 ng, err = txn.Current("bar") 207 require.NoError(t, err) 208 require.NotNil(t, ng) 209 require.Equal(t, "mybuild", ng.Name) 210 211 ng, err = txn.Current("foo") 212 require.NoError(t, err) 213 require.Nil(t, ng) 214 215 err = txn.SetCurrent("bar", "mybuild", false, true) 216 require.NoError(t, err) 217 218 err = txn.SetCurrent("foo", "mybuild2", false, false) 219 require.NoError(t, err) 220 221 // test removal 222 err = txn.Remove("mybuild2") 223 require.NoError(t, err) 224 225 _, err = txn.NodeGroupByName("mybuild2") 226 require.Error(t, err) 227 require.True(t, os.IsNotExist(errors.Cause(err))) 228 229 ng, err = txn.Current("foo") 230 require.NoError(t, err) 231 require.Nil(t, ng) 232 233 ng, err = txn.Current("bar") 234 require.NoError(t, err) 235 require.NotNil(t, ng) 236 require.Equal(t, "mybuild", ng.Name) 237 } 238 239 func TestNodeInvalidName(t *testing.T) { 240 t.Parallel() 241 tmpdir := t.TempDir() 242 243 s, err := New(tmpdir) 244 require.NoError(t, err) 245 246 txn, release, err := s.Txn() 247 require.NoError(t, err) 248 defer release() 249 250 _, err = txn.NodeGroupByName("123builder") 251 require.Error(t, err) 252 require.True(t, IsErrInvalidName(err)) 253 254 err = txn.Save(&NodeGroup{ 255 Name: "123builder", 256 Driver: "mydriver", 257 }) 258 require.Error(t, err) 259 require.True(t, IsErrInvalidName(err)) 260 }