github.com/apptainer/singularity@v3.1.1+incompatible/internal/pkg/syecl/syecl_test.go (about) 1 // Copyright (c) 2018, Sylabs Inc. All rights reserved. 2 // This software is licensed under a 3-clause BSD license. Please consult the 3 // LICENSE.md file distributed with the sources of this project regarding your 4 // rights to use or distribute this software. 5 6 package syecl 7 8 import ( 9 "io" 10 "io/ioutil" 11 "os" 12 "path/filepath" 13 "testing" 14 ) 15 16 const ( 17 KeyFP1 = "5994BE54C31CF1B5E1994F987C52CF6D055F072B" 18 KeyFP2 = "7064B1D6EFF01B1262FED3F03581D99FE87EAFD1" 19 ) 20 21 var ( 22 srcContainer1 = filepath.Join("testdata", "container1.sif") 23 srcContainer2 = filepath.Join("testdata", "container2.sif") 24 srcContainer3 = filepath.Join("testdata", "container3.sif") 25 ) 26 27 var ( 28 testEclFileName string // pathname of the Ecl config file 29 testEclFileName2 string // pathname of the Ecl config file 30 testEclDirPath1 string // dirname of the first Ecl execgroup 31 testEclDirPath2 string // dirname of the second Ecl execgroup 32 testEclDirPath3 string // dirname of the third Ecl execgroup 33 testContainer1 string // pathname of the first test container 34 testContainer2 string // pathname of the second test container 35 testContainer3 string // pathname of the third test container 36 testContainer4 string // pathname of the forth test container 37 ) 38 39 var testEclConfig = EclConfig{ 40 Activated: true, 41 ExecGroups: []execgroup{ 42 {"group1", "whitelist", "", []string{KeyFP1, KeyFP2}}, 43 {"group2", "whitestrict", "", []string{KeyFP1, KeyFP2}}, 44 {"group3", "blacklist", "", []string{KeyFP1}}, 45 }, 46 } 47 48 var testEclConfig2 = EclConfig{ 49 Activated: true, 50 ExecGroups: []execgroup{ 51 {"pathdup", "whitelist", "/tmp", nil}, 52 {"pathdup", "whitelist", "/tmp", nil}, 53 }, 54 } 55 56 func TestAPutConfig(t *testing.T) { 57 err := PutConfig(testEclConfig, testEclFileName) 58 if err != nil { 59 t.Error(`PutConfig(testEclConfig, testEclFileName):`, err) 60 } 61 err = PutConfig(testEclConfig2, testEclFileName2) 62 if err != nil { 63 t.Error(`PutConfig(testEclConfig2, testEclFileName2):`, err) 64 } 65 } 66 67 func TestLoadConfig(t *testing.T) { 68 ecl, err := LoadConfig(testEclFileName) 69 if err != nil { 70 t.Error(`LoadConfig(testEclFileName):`, err) 71 } 72 if ecl.Activated == false { 73 t.Error("the ECL should be activated") 74 } 75 if ecl.ExecGroups[0].DirPath != testEclDirPath1 { 76 t.Error("the path was expected to be:", testEclDirPath1) 77 } 78 if ecl.ExecGroups[0].KeyFPs[0] != KeyFP1 { 79 t.Error("the entity was expected to be:", KeyFP1) 80 } 81 } 82 83 func TestValidateConfig(t *testing.T) { 84 // Validate properly formed config file 85 ecl, err := LoadConfig(testEclFileName) 86 if err != nil { 87 t.Error(`LoadConfig(testEclFileName):`, err) 88 } 89 if err = ecl.ValidateConfig(); err != nil { 90 t.Error(`ecl.ValidateConfig():`, err) 91 } 92 93 // Validate config file with duplicated dirpaths 94 ecl, err = LoadConfig(testEclFileName2) 95 if err != nil { 96 t.Error(`LoadConfig(testEclFileName2):`, err) 97 } 98 if err = ecl.ValidateConfig(); err == nil { 99 t.Error(`ecl.ValidateConfig(): Should have detected duplicated dirpaths`, err) 100 } 101 } 102 103 func TestShouldRun(t *testing.T) { 104 ecl, err := LoadConfig(testEclFileName) 105 if err != nil { 106 t.Error(`LoadConfig(testEclFileName):`, err) 107 } 108 109 if err = ecl.ValidateConfig(); err != nil { 110 t.Error(`ecl.ValidateConfig():`, err) 111 } 112 113 // check container1 authorization 114 run, err := ecl.ShouldRun(testContainer1) 115 if err != nil { 116 t.Error(`ecl.ShouldRun(testContainer1):`, err) 117 } 118 if !run { 119 t.Error(testContainer1, "should be allowed to run") 120 } 121 // check container2 authorization 122 run, err = ecl.ShouldRun(testContainer2) 123 if err != nil { 124 t.Error(`ecl.ShouldRun(testContainer2):`, err) 125 } 126 if !run { 127 t.Error(testContainer2, "should be allowed to run") 128 } 129 // check container3 authorization (fails with KeyFP) 130 run, err = ecl.ShouldRun(testContainer3) 131 if err == nil || run == true { 132 t.Error(testContainer3, "should NOT be allowed to run") 133 } 134 // check srcContainer1 authorization (fails with dirpath) 135 run, err = ecl.ShouldRun(srcContainer1) 136 if err == nil || run == true { 137 t.Error(srcContainer1, "should NOT be allowed to run") 138 } 139 // check container4 authorization (fails with blacklist) 140 run, err = ecl.ShouldRun(testContainer4) 141 if err == nil || run == true { 142 t.Error(testContainer4, "should NOT be allowed to run") 143 } 144 145 // in this second round of tests, set DirPath to "", and test container in testdata/ 146 ecl.ExecGroups[0].DirPath = "" 147 ecl.ExecGroups[1].DirPath = "" 148 149 // check container1 authorization (outside of defined dirpath) 150 run, err = ecl.ShouldRun(srcContainer1) 151 if err != nil { 152 t.Error(`ecl.ShouldRun(srcContainer1):`, err) 153 } 154 if !run { 155 t.Error(srcContainer1, "should be allowed to run") 156 } 157 } 158 159 func copyFile(dst, src string) error { 160 s, err := os.Open(src) 161 if err != nil { 162 return err 163 } 164 defer s.Close() 165 166 d, err := os.Create(dst) 167 if err != nil { 168 return err 169 } 170 171 if _, err := io.Copy(d, s); err != nil { 172 d.Close() 173 return err 174 } 175 176 return d.Close() 177 } 178 179 func setup() error { 180 // Use TempFile to create a placeholder for the ECL config test files 181 tmpfile, err := ioutil.TempFile("", "eclconfig-test") 182 if err != nil { 183 return nil 184 } 185 testEclFileName = tmpfile.Name() 186 tmpfile.Close() 187 188 tmpfile, err = ioutil.TempFile("", "eclconfig2-test") 189 if err != nil { 190 return nil 191 } 192 testEclFileName2 = tmpfile.Name() 193 tmpfile.Close() 194 195 // Create three directories where we put test containers 196 testEclDirPath1, err = ioutil.TempDir("", "ecldir1-") 197 if err != nil { 198 return err 199 } 200 201 testEclDirPath2, err = ioutil.TempDir("", "ecldir2-") 202 if err != nil { 203 return err 204 } 205 206 testEclDirPath3, err = ioutil.TempDir("", "ecldir3-") 207 if err != nil { 208 return err 209 } 210 211 // Set the just created Dirpaths in the EclConfig struct to marshal 212 testEclConfig.ExecGroups[0].DirPath = testEclDirPath1 213 testEclConfig.ExecGroups[1].DirPath = testEclDirPath2 214 testEclConfig.ExecGroups[2].DirPath = testEclDirPath3 215 216 // prepare and copy test containers from testdata/* to their test dirpaths 217 testContainer1 = filepath.Join(testEclDirPath1, filepath.Base(srcContainer1)) 218 if err := copyFile(testContainer1, srcContainer1); err != nil { 219 return err 220 } 221 testContainer2 = filepath.Join(testEclDirPath2, filepath.Base(srcContainer2)) 222 if err := copyFile(testContainer2, srcContainer2); err != nil { 223 return err 224 } 225 testContainer3 = filepath.Join(testEclDirPath2, filepath.Base(srcContainer3)) 226 if err := copyFile(testContainer3, srcContainer3); err != nil { 227 return err 228 } 229 testContainer4 = filepath.Join(testEclDirPath3, filepath.Base(srcContainer3)) 230 return copyFile(testContainer4, srcContainer3) 231 } 232 233 func shutdown() { 234 os.Remove(testEclFileName) 235 os.Remove(testEclFileName2) 236 os.RemoveAll(testEclDirPath1) 237 os.RemoveAll(testEclDirPath2) 238 os.RemoveAll(testEclDirPath3) 239 } 240 241 func TestMain(m *testing.M) { 242 if err := setup(); err != nil { 243 shutdown() 244 os.Exit(2) 245 } 246 ret := m.Run() 247 shutdown() 248 os.Exit(ret) 249 }