github.com/xeptore/docker-cli@v20.10.14+incompatible/cli/command/inspect/inspector_test.go (about) 1 package inspect 2 3 import ( 4 "bytes" 5 "strings" 6 "testing" 7 8 "github.com/docker/cli/templates" 9 "gotest.tools/v3/assert" 10 is "gotest.tools/v3/assert/cmp" 11 ) 12 13 type testElement struct { 14 DNS string `json:"Dns"` 15 } 16 17 func TestTemplateInspectorDefault(t *testing.T) { 18 b := new(bytes.Buffer) 19 tmpl, err := templates.Parse("{{.DNS}}") 20 if err != nil { 21 t.Fatal(err) 22 } 23 i := NewTemplateInspector(b, tmpl) 24 if err := i.Inspect(testElement{"0.0.0.0"}, nil); err != nil { 25 t.Fatal(err) 26 } 27 28 if err := i.Flush(); err != nil { 29 t.Fatal(err) 30 } 31 if b.String() != "0.0.0.0\n" { 32 t.Fatalf("Expected `0.0.0.0\\n`, got `%s`", b.String()) 33 } 34 } 35 36 func TestTemplateInspectorEmpty(t *testing.T) { 37 b := new(bytes.Buffer) 38 tmpl, err := templates.Parse("{{.DNS}}") 39 if err != nil { 40 t.Fatal(err) 41 } 42 i := NewTemplateInspector(b, tmpl) 43 44 if err := i.Flush(); err != nil { 45 t.Fatal(err) 46 } 47 if b.String() != "\n" { 48 t.Fatalf("Expected `\\n`, got `%s`", b.String()) 49 } 50 } 51 52 func TestTemplateInspectorTemplateError(t *testing.T) { 53 b := new(bytes.Buffer) 54 tmpl, err := templates.Parse("{{.Foo}}") 55 if err != nil { 56 t.Fatal(err) 57 } 58 i := NewTemplateInspector(b, tmpl) 59 60 err = i.Inspect(testElement{"0.0.0.0"}, nil) 61 if err == nil { 62 t.Fatal("Expected error got nil") 63 } 64 65 if !strings.HasPrefix(err.Error(), "Template parsing error") { 66 t.Fatalf("Expected template error, got %v", err) 67 } 68 } 69 70 func TestTemplateInspectorRawFallback(t *testing.T) { 71 b := new(bytes.Buffer) 72 tmpl, err := templates.Parse("{{.Dns}}") 73 if err != nil { 74 t.Fatal(err) 75 } 76 i := NewTemplateInspector(b, tmpl) 77 if err := i.Inspect(testElement{"0.0.0.0"}, []byte(`{"Dns": "0.0.0.0"}`)); err != nil { 78 t.Fatal(err) 79 } 80 81 if err := i.Flush(); err != nil { 82 t.Fatal(err) 83 } 84 if b.String() != "0.0.0.0\n" { 85 t.Fatalf("Expected `0.0.0.0\\n`, got `%s`", b.String()) 86 } 87 } 88 89 func TestTemplateInspectorRawFallbackError(t *testing.T) { 90 b := new(bytes.Buffer) 91 tmpl, err := templates.Parse("{{.Dns}}") 92 if err != nil { 93 t.Fatal(err) 94 } 95 i := NewTemplateInspector(b, tmpl) 96 err = i.Inspect(testElement{"0.0.0.0"}, []byte(`{"Foo": "0.0.0.0"}`)) 97 if err == nil { 98 t.Fatal("Expected error got nil") 99 } 100 101 if !strings.HasPrefix(err.Error(), "Template parsing error") { 102 t.Fatalf("Expected template error, got %v", err) 103 } 104 } 105 106 func TestTemplateInspectorMultiple(t *testing.T) { 107 b := new(bytes.Buffer) 108 tmpl, err := templates.Parse("{{.DNS}}") 109 if err != nil { 110 t.Fatal(err) 111 } 112 i := NewTemplateInspector(b, tmpl) 113 114 if err := i.Inspect(testElement{"0.0.0.0"}, nil); err != nil { 115 t.Fatal(err) 116 } 117 if err := i.Inspect(testElement{"1.1.1.1"}, nil); err != nil { 118 t.Fatal(err) 119 } 120 121 if err := i.Flush(); err != nil { 122 t.Fatal(err) 123 } 124 if b.String() != "0.0.0.0\n1.1.1.1\n" { 125 t.Fatalf("Expected `0.0.0.0\\n1.1.1.1\\n`, got `%s`", b.String()) 126 } 127 } 128 129 func TestIndentedInspectorDefault(t *testing.T) { 130 b := new(bytes.Buffer) 131 i := NewIndentedInspector(b) 132 if err := i.Inspect(testElement{"0.0.0.0"}, nil); err != nil { 133 t.Fatal(err) 134 } 135 136 if err := i.Flush(); err != nil { 137 t.Fatal(err) 138 } 139 140 expected := `[ 141 { 142 "Dns": "0.0.0.0" 143 } 144 ] 145 ` 146 if b.String() != expected { 147 t.Fatalf("Expected `%s`, got `%s`", expected, b.String()) 148 } 149 } 150 151 func TestIndentedInspectorMultiple(t *testing.T) { 152 b := new(bytes.Buffer) 153 i := NewIndentedInspector(b) 154 if err := i.Inspect(testElement{"0.0.0.0"}, nil); err != nil { 155 t.Fatal(err) 156 } 157 158 if err := i.Inspect(testElement{"1.1.1.1"}, nil); err != nil { 159 t.Fatal(err) 160 } 161 162 if err := i.Flush(); err != nil { 163 t.Fatal(err) 164 } 165 166 expected := `[ 167 { 168 "Dns": "0.0.0.0" 169 }, 170 { 171 "Dns": "1.1.1.1" 172 } 173 ] 174 ` 175 if b.String() != expected { 176 t.Fatalf("Expected `%s`, got `%s`", expected, b.String()) 177 } 178 } 179 180 func TestIndentedInspectorEmpty(t *testing.T) { 181 b := new(bytes.Buffer) 182 i := NewIndentedInspector(b) 183 184 if err := i.Flush(); err != nil { 185 t.Fatal(err) 186 } 187 188 expected := "[]\n" 189 if b.String() != expected { 190 t.Fatalf("Expected `%s`, got `%s`", expected, b.String()) 191 } 192 } 193 194 func TestIndentedInspectorRawElements(t *testing.T) { 195 b := new(bytes.Buffer) 196 i := NewIndentedInspector(b) 197 if err := i.Inspect(testElement{"0.0.0.0"}, []byte(`{"Dns": "0.0.0.0", "Node": "0"}`)); err != nil { 198 t.Fatal(err) 199 } 200 201 if err := i.Inspect(testElement{"1.1.1.1"}, []byte(`{"Dns": "1.1.1.1", "Node": "1"}`)); err != nil { 202 t.Fatal(err) 203 } 204 205 if err := i.Flush(); err != nil { 206 t.Fatal(err) 207 } 208 209 expected := `[ 210 { 211 "Dns": "0.0.0.0", 212 "Node": "0" 213 }, 214 { 215 "Dns": "1.1.1.1", 216 "Node": "1" 217 } 218 ] 219 ` 220 if b.String() != expected { 221 t.Fatalf("Expected `%s`, got `%s`", expected, b.String()) 222 } 223 } 224 225 // moby/moby#32235 226 // This test verifies that even if `tryRawInspectFallback` is called the fields containing 227 // numerical values are displayed correctly. 228 // For example, `docker inspect --format "{{.Id}} {{.Size}} alpine` and 229 // `docker inspect --format "{{.ID}} {{.Size}} alpine" will have the same output which is 230 // sha256:651aa95985aa4a17a38ffcf71f598ec461924ca96865facc2c5782ef2d2be07f 3983636 231 func TestTemplateInspectorRawFallbackNumber(t *testing.T) { 232 // Using typedElem to automatically fall to tryRawInspectFallback. 233 typedElem := struct { 234 ID string `json:"Id"` 235 }{"ad3"} 236 testcases := []struct { 237 raw []byte 238 exp string 239 }{ 240 {raw: []byte(`{"Id": "ad3", "Size": 53317}`), exp: "53317 ad3\n"}, 241 {raw: []byte(`{"Id": "ad3", "Size": 53317.102}`), exp: "53317.102 ad3\n"}, 242 {raw: []byte(`{"Id": "ad3", "Size": 53317.0}`), exp: "53317.0 ad3\n"}, 243 } 244 b := new(bytes.Buffer) 245 tmpl, err := templates.Parse("{{.Size}} {{.Id}}") 246 assert.NilError(t, err) 247 248 i := NewTemplateInspector(b, tmpl) 249 for _, tc := range testcases { 250 err = i.Inspect(typedElem, tc.raw) 251 assert.NilError(t, err) 252 253 err = i.Flush() 254 assert.NilError(t, err) 255 256 assert.Check(t, is.Equal(tc.exp, b.String())) 257 b.Reset() 258 } 259 }