github.com/hairyhenderson/templater@v3.5.0+incompatible/template_test.go (about) 1 package gomplate 2 3 import ( 4 "bytes" 5 "io" 6 "io/ioutil" 7 "os" 8 "testing" 9 10 "github.com/spf13/afero" 11 12 "github.com/stretchr/testify/assert" 13 ) 14 15 func TestReadInput(t *testing.T) { 16 origfs := fs 17 defer func() { fs = origfs }() 18 fs = afero.NewMemMapFs() 19 _ = fs.Mkdir("/tmp", 0777) 20 f, _ := fs.Create("/tmp/foo") 21 _, _ = f.Write([]byte("foo")) 22 23 f, _ = fs.Create("/tmp/unreadable") 24 _, _ = f.Write([]byte("foo")) 25 26 actual, err := readInput("/tmp/foo") 27 assert.NoError(t, err) 28 assert.Equal(t, "foo", actual) 29 30 defer func() { stdin = os.Stdin }() 31 stdin = ioutil.NopCloser(bytes.NewBufferString("bar")) 32 33 actual, err = readInput("-") 34 assert.NoError(t, err) 35 assert.Equal(t, "bar", actual) 36 37 _, err = readInput("bogus") 38 assert.Error(t, err) 39 } 40 41 func TestOpenOutFile(t *testing.T) { 42 origfs := fs 43 defer func() { fs = origfs }() 44 fs = afero.NewMemMapFs() 45 _ = fs.Mkdir("/tmp", 0777) 46 47 _, err := openOutFile("/tmp/foo", 0644, false) 48 assert.NoError(t, err) 49 i, err := fs.Stat("/tmp/foo") 50 assert.NoError(t, err) 51 assert.Equal(t, os.FileMode(0644), i.Mode()) 52 53 defer func() { Stdout = os.Stdout }() 54 Stdout = &nopWCloser{&bytes.Buffer{}} 55 56 f, err := openOutFile("-", 0644, false) 57 assert.NoError(t, err) 58 assert.Equal(t, Stdout, f) 59 } 60 61 func TestLoadContents(t *testing.T) { 62 origfs := fs 63 defer func() { fs = origfs }() 64 fs = afero.NewMemMapFs() 65 66 afero.WriteFile(fs, "foo", []byte("contents"), 0644) 67 68 tmpl := &tplate{name: "foo"} 69 err := tmpl.loadContents() 70 assert.NoError(t, err) 71 assert.Equal(t, "contents", tmpl.contents) 72 } 73 74 func TestAddTarget(t *testing.T) { 75 origfs := fs 76 defer func() { fs = origfs }() 77 fs = afero.NewMemMapFs() 78 79 tmpl := &tplate{name: "foo", targetPath: "/out/outfile"} 80 err := tmpl.addTarget() 81 assert.NoError(t, err) 82 assert.NotNil(t, tmpl.target) 83 } 84 85 func TestGatherTemplates(t *testing.T) { 86 origfs := fs 87 defer func() { fs = origfs }() 88 fs = afero.NewMemMapFs() 89 afero.WriteFile(fs, "foo", []byte("bar"), 0600) 90 91 afero.WriteFile(fs, "in/1", []byte("foo"), 0644) 92 afero.WriteFile(fs, "in/2", []byte("bar"), 0644) 93 afero.WriteFile(fs, "in/3", []byte("baz"), 0644) 94 95 templates, err := gatherTemplates(&Config{}, nil) 96 assert.NoError(t, err) 97 assert.Len(t, templates, 1) 98 99 templates, err = gatherTemplates(&Config{ 100 Input: "foo", 101 }, nil) 102 assert.NoError(t, err) 103 assert.Len(t, templates, 1) 104 assert.Equal(t, "foo", templates[0].contents) 105 assert.Equal(t, Stdout, templates[0].target) 106 107 templates, err = gatherTemplates(&Config{ 108 Input: "foo", 109 OutputFiles: []string{"out"}, 110 }, nil) 111 assert.NoError(t, err) 112 assert.Len(t, templates, 1) 113 assert.Equal(t, "out", templates[0].targetPath) 114 assert.Equal(t, os.FileMode(0644), templates[0].mode) 115 info, err := fs.Stat("out") 116 assert.NoError(t, err) 117 assert.Equal(t, os.FileMode(0644), info.Mode()) 118 fs.Remove("out") 119 120 templates, err = gatherTemplates(&Config{ 121 InputFiles: []string{"foo"}, 122 OutputFiles: []string{"out"}, 123 }, nil) 124 assert.NoError(t, err) 125 assert.Len(t, templates, 1) 126 assert.Equal(t, "bar", templates[0].contents) 127 assert.NotEqual(t, Stdout, templates[0].target) 128 assert.Equal(t, os.FileMode(0600), templates[0].mode) 129 info, err = fs.Stat("out") 130 assert.NoError(t, err) 131 assert.Equal(t, os.FileMode(0600), info.Mode()) 132 fs.Remove("out") 133 134 templates, err = gatherTemplates(&Config{ 135 InputFiles: []string{"foo"}, 136 OutputFiles: []string{"out"}, 137 OutMode: "755", 138 }, nil) 139 assert.NoError(t, err) 140 assert.Len(t, templates, 1) 141 assert.Equal(t, "bar", templates[0].contents) 142 assert.NotEqual(t, Stdout, templates[0].target) 143 assert.Equal(t, os.FileMode(0755), templates[0].mode) 144 info, err = fs.Stat("out") 145 assert.NoError(t, err) 146 assert.Equal(t, os.FileMode(0755), info.Mode()) 147 fs.Remove("out") 148 149 templates, err = gatherTemplates(&Config{ 150 InputDir: "in", 151 OutputDir: "out", 152 }, simpleNamer("out")) 153 assert.NoError(t, err) 154 assert.Len(t, templates, 3) 155 assert.Equal(t, "foo", templates[0].contents) 156 fs.Remove("out") 157 } 158 159 func TestProcessTemplates(t *testing.T) { 160 origfs := fs 161 defer func() { fs = origfs }() 162 fs = afero.NewMemMapFs() 163 afero.WriteFile(fs, "foo", []byte("bar"), 0600) 164 165 afero.WriteFile(fs, "in/1", []byte("foo"), 0644) 166 afero.WriteFile(fs, "in/2", []byte("bar"), 0640) 167 afero.WriteFile(fs, "in/3", []byte("baz"), 0644) 168 169 afero.WriteFile(fs, "existing", []byte(""), 0644) 170 171 testdata := []struct { 172 templates []*tplate 173 contents []string 174 modes []os.FileMode 175 targets []io.WriteCloser 176 }{ 177 {}, 178 { 179 templates: []*tplate{{name: "<arg>", contents: "foo", targetPath: "-", mode: 0644}}, 180 contents: []string{"foo"}, 181 modes: []os.FileMode{0644}, 182 targets: []io.WriteCloser{Stdout}, 183 }, 184 { 185 templates: []*tplate{{name: "<arg>", contents: "foo", targetPath: "out", mode: 0644}}, 186 contents: []string{"foo"}, 187 modes: []os.FileMode{0644}, 188 }, 189 { 190 templates: []*tplate{{name: "foo", targetPath: "out", mode: 0600}}, 191 contents: []string{"bar"}, 192 modes: []os.FileMode{0600}, 193 }, 194 { 195 templates: []*tplate{{name: "foo", targetPath: "out", mode: 0755}}, 196 contents: []string{"bar"}, 197 modes: []os.FileMode{0755}, 198 }, 199 { 200 templates: []*tplate{ 201 {name: "in/1", targetPath: "out/1", mode: 0644}, 202 {name: "in/2", targetPath: "out/2", mode: 0640}, 203 {name: "in/3", targetPath: "out/3", mode: 0644}, 204 }, 205 contents: []string{"foo", "bar", "baz"}, 206 modes: []os.FileMode{0644, 0640, 0644}, 207 }, 208 { 209 templates: []*tplate{ 210 {name: "foo", targetPath: "existing", mode: 0755}, 211 }, 212 contents: []string{"bar"}, 213 modes: []os.FileMode{0644}, 214 }, 215 { 216 templates: []*tplate{ 217 {name: "foo", targetPath: "existing", mode: 0755, modeOverride: true}, 218 }, 219 contents: []string{"bar"}, 220 modes: []os.FileMode{0755}, 221 }, 222 } 223 for _, in := range testdata { 224 actual, err := processTemplates(in.templates) 225 assert.NoError(t, err) 226 assert.Len(t, actual, len(in.templates)) 227 for i, a := range actual { 228 assert.Equal(t, in.contents[i], a.contents) 229 assert.Equal(t, in.templates[i].mode, a.mode) 230 if len(in.targets) > 0 { 231 assert.Equal(t, in.targets[i], a.target) 232 } 233 if in.templates[i].targetPath != "-" { 234 info, err := fs.Stat(in.templates[i].targetPath) 235 assert.NoError(t, err) 236 assert.Equal(t, in.modes[i], info.Mode()) 237 } 238 } 239 fs.Remove("out") 240 } 241 } 242 243 func TestAllWhitespace(t *testing.T) { 244 testdata := []struct { 245 in []byte 246 expected bool 247 }{ 248 {[]byte(" "), true}, 249 {[]byte("foo"), false}, 250 {[]byte(" \t\n\n\v\r\n"), true}, 251 {[]byte(" foo "), false}, 252 } 253 254 for _, d := range testdata { 255 assert.Equal(t, d.expected, allWhitespace(d.in)) 256 } 257 } 258 259 func TestEmptySkipper(t *testing.T) { 260 testdata := []struct { 261 in []byte 262 empty bool 263 }{ 264 {[]byte(" "), true}, 265 {[]byte("foo"), false}, 266 {[]byte(" \t\n\n\v\r\n"), true}, 267 {[]byte(" foo "), false}, 268 } 269 270 for _, d := range testdata { 271 w := &bufferCloser{&bytes.Buffer{}} 272 opened := false 273 f := newEmptySkipper(func() (io.WriteCloser, error) { 274 t.Logf("I got called %#v", w) 275 opened = true 276 return w, nil 277 }) 278 n, err := f.Write(d.in) 279 assert.NoError(t, err) 280 assert.Equal(t, len(d.in), n) 281 if d.empty { 282 assert.Nil(t, f.w) 283 assert.False(t, opened) 284 } else { 285 assert.NotNil(t, f.w) 286 assert.True(t, opened) 287 assert.EqualValues(t, d.in, w.Bytes()) 288 } 289 } 290 } 291 292 type bufferCloser struct { 293 *bytes.Buffer 294 } 295 296 func (b *bufferCloser) Close() error { 297 return nil 298 }