github.com/fastly/cli@v1.7.2-0.20240304164155-9d0f1d77c3bf/pkg/commands/logging/newrelic/newrelic_test.go (about) 1 package newrelic_test 2 3 import ( 4 "bytes" 5 "io" 6 "testing" 7 8 "github.com/fastly/go-fastly/v9/fastly" 9 10 "github.com/fastly/cli/pkg/app" 11 "github.com/fastly/cli/pkg/global" 12 "github.com/fastly/cli/pkg/mock" 13 "github.com/fastly/cli/pkg/testutil" 14 ) 15 16 func TestNewRelicCreate(t *testing.T) { 17 args := testutil.Args 18 scenarios := []testutil.TestScenario{ 19 { 20 Name: "validate missing --service-id flag", 21 Args: args("logging newrelic create --key abc --name foo --version 3"), 22 WantError: "error reading service: no service ID found", 23 }, 24 { 25 Name: "validate missing --autoclone flag", 26 API: mock.API{ 27 ListVersionsFn: testutil.ListVersions, 28 }, 29 Args: args("logging newrelic create --key abc --name foo --service-id 123 --version 1"), 30 WantError: "service version 1 is not editable", 31 }, 32 { 33 Name: "validate CreateNewRelic API error", 34 API: mock.API{ 35 ListVersionsFn: testutil.ListVersions, 36 CreateNewRelicFn: func(i *fastly.CreateNewRelicInput) (*fastly.NewRelic, error) { 37 return nil, testutil.Err 38 }, 39 }, 40 Args: args("logging newrelic create --key abc --name foo --service-id 123 --version 3"), 41 WantError: testutil.Err.Error(), 42 }, 43 { 44 Name: "validate CreateNewRelic API success", 45 API: mock.API{ 46 ListVersionsFn: testutil.ListVersions, 47 CreateNewRelicFn: func(i *fastly.CreateNewRelicInput) (*fastly.NewRelic, error) { 48 return &fastly.NewRelic{ 49 Name: i.Name, 50 ServiceID: fastly.ToPointer(i.ServiceID), 51 ServiceVersion: fastly.ToPointer(i.ServiceVersion), 52 }, nil 53 }, 54 }, 55 Args: args("logging newrelic create --key abc --name foo --service-id 123 --version 3"), 56 WantOutput: "Created New Relic logging endpoint 'foo' (service: 123, version: 3)", 57 }, 58 { 59 Name: "validate --autoclone results in cloned service version", 60 API: mock.API{ 61 ListVersionsFn: testutil.ListVersions, 62 CloneVersionFn: testutil.CloneVersionResult(4), 63 CreateNewRelicFn: func(i *fastly.CreateNewRelicInput) (*fastly.NewRelic, error) { 64 return &fastly.NewRelic{ 65 Name: i.Name, 66 ServiceID: fastly.ToPointer(i.ServiceID), 67 ServiceVersion: fastly.ToPointer(i.ServiceVersion), 68 }, nil 69 }, 70 }, 71 Args: args("logging newrelic create --autoclone --key abc --name foo --service-id 123 --version 1"), 72 WantOutput: "Created New Relic logging endpoint 'foo' (service: 123, version: 4)", 73 }, 74 } 75 76 for testcaseIdx := range scenarios { 77 testcase := &scenarios[testcaseIdx] 78 t.Run(testcase.Name, func(t *testing.T) { 79 var stdout bytes.Buffer 80 app.Init = func(_ []string, _ io.Reader) (*global.Data, error) { 81 opts := testutil.MockGlobalData(testcase.Args, &stdout) 82 opts.APIClientFactory = mock.APIClient(testcase.API) 83 return opts, nil 84 } 85 err := app.Run(testcase.Args, nil) 86 testutil.AssertErrorContains(t, err, testcase.WantError) 87 testutil.AssertStringContains(t, stdout.String(), testcase.WantOutput) 88 }) 89 } 90 } 91 92 func TestNewRelicDelete(t *testing.T) { 93 args := testutil.Args 94 scenarios := []testutil.TestScenario{ 95 { 96 Name: "validate missing --name flag", 97 Args: args("logging newrelic delete --version 3"), 98 WantError: "error parsing arguments: required flag --name not provided", 99 }, 100 { 101 Name: "validate missing --version flag", 102 Args: args("logging newrelic delete --name foobar"), 103 WantError: "error parsing arguments: required flag --version not provided", 104 }, 105 { 106 Name: "validate missing --service-id flag", 107 Args: args("logging newrelic delete --name foobar --version 3"), 108 WantError: "error reading service: no service ID found", 109 }, 110 { 111 Name: "validate missing --autoclone flag", 112 API: mock.API{ 113 ListVersionsFn: testutil.ListVersions, 114 }, 115 Args: args("logging newrelic delete --name foobar --service-id 123 --version 1"), 116 WantError: "service version 1 is not editable", 117 }, 118 { 119 Name: "validate DeleteNewRelic API error", 120 API: mock.API{ 121 ListVersionsFn: testutil.ListVersions, 122 DeleteNewRelicFn: func(i *fastly.DeleteNewRelicInput) error { 123 return testutil.Err 124 }, 125 }, 126 Args: args("logging newrelic delete --name foobar --service-id 123 --version 3"), 127 WantError: testutil.Err.Error(), 128 }, 129 { 130 Name: "validate DeleteNewRelic API success", 131 API: mock.API{ 132 ListVersionsFn: testutil.ListVersions, 133 DeleteNewRelicFn: func(i *fastly.DeleteNewRelicInput) error { 134 return nil 135 }, 136 }, 137 Args: args("logging newrelic delete --name foobar --service-id 123 --version 3"), 138 WantOutput: "Deleted New Relic logging endpoint 'foobar' (service: 123, version: 3)", 139 }, 140 { 141 Name: "validate --autoclone results in cloned service version", 142 API: mock.API{ 143 ListVersionsFn: testutil.ListVersions, 144 CloneVersionFn: testutil.CloneVersionResult(4), 145 DeleteNewRelicFn: func(i *fastly.DeleteNewRelicInput) error { 146 return nil 147 }, 148 }, 149 Args: args("logging newrelic delete --autoclone --name foo --service-id 123 --version 1"), 150 WantOutput: "Deleted New Relic logging endpoint 'foo' (service: 123, version: 4)", 151 }, 152 } 153 154 for testcaseIdx := range scenarios { 155 testcase := &scenarios[testcaseIdx] 156 t.Run(testcase.Name, func(t *testing.T) { 157 var stdout bytes.Buffer 158 app.Init = func(_ []string, _ io.Reader) (*global.Data, error) { 159 opts := testutil.MockGlobalData(testcase.Args, &stdout) 160 opts.APIClientFactory = mock.APIClient(testcase.API) 161 return opts, nil 162 } 163 err := app.Run(testcase.Args, nil) 164 testutil.AssertErrorContains(t, err, testcase.WantError) 165 testutil.AssertStringContains(t, stdout.String(), testcase.WantOutput) 166 }) 167 } 168 } 169 170 func TestNewRelicDescribe(t *testing.T) { 171 args := testutil.Args 172 scenarios := []testutil.TestScenario{ 173 { 174 Name: "validate missing --name flag", 175 Args: args("logging newrelic describe --version 3"), 176 WantError: "error parsing arguments: required flag --name not provided", 177 }, 178 { 179 Name: "validate missing --version flag", 180 Args: args("logging newrelic describe --name foobar"), 181 WantError: "error parsing arguments: required flag --version not provided", 182 }, 183 { 184 Name: "validate missing --service-id flag", 185 Args: args("logging newrelic describe --name foobar --version 3"), 186 WantError: "error reading service: no service ID found", 187 }, 188 { 189 Name: "validate GetNewRelic API error", 190 API: mock.API{ 191 ListVersionsFn: testutil.ListVersions, 192 GetNewRelicFn: func(i *fastly.GetNewRelicInput) (*fastly.NewRelic, error) { 193 return nil, testutil.Err 194 }, 195 }, 196 Args: args("logging newrelic describe --name foobar --service-id 123 --version 3"), 197 WantError: testutil.Err.Error(), 198 }, 199 { 200 Name: "validate GetNewRelic API success", 201 API: mock.API{ 202 ListVersionsFn: testutil.ListVersions, 203 GetNewRelicFn: getNewRelic, 204 }, 205 Args: args("logging newrelic describe --name foobar --service-id 123 --version 3"), 206 WantOutput: "\nCreated at: 2021-06-15 23:00:00 +0000 UTC\nDeleted at: 2021-06-15 23:00:00 +0000 UTC\nFormat: \nFormat Version: 0\nName: foobar\nPlacement: \nRegion: \nResponse Condition: \nService ID: 123\nService Version: 3\nToken: abc\nUpdated at: 2021-06-15 23:00:00 +0000 UTC\n", 207 }, 208 { 209 Name: "validate missing --autoclone flag is OK", 210 API: mock.API{ 211 ListVersionsFn: testutil.ListVersions, 212 GetNewRelicFn: getNewRelic, 213 }, 214 Args: args("logging newrelic describe --name foobar --service-id 123 --version 1"), 215 WantOutput: "\nCreated at: 2021-06-15 23:00:00 +0000 UTC\nDeleted at: 2021-06-15 23:00:00 +0000 UTC\nFormat: \nFormat Version: 0\nName: foobar\nPlacement: \nRegion: \nResponse Condition: \nService ID: 123\nService Version: 1\nToken: abc\nUpdated at: 2021-06-15 23:00:00 +0000 UTC\n", 216 }, 217 } 218 219 for testcaseIdx := range scenarios { 220 testcase := &scenarios[testcaseIdx] 221 t.Run(testcase.Name, func(t *testing.T) { 222 var stdout bytes.Buffer 223 app.Init = func(_ []string, _ io.Reader) (*global.Data, error) { 224 opts := testutil.MockGlobalData(testcase.Args, &stdout) 225 opts.APIClientFactory = mock.APIClient(testcase.API) 226 return opts, nil 227 } 228 err := app.Run(testcase.Args, nil) 229 testutil.AssertErrorContains(t, err, testcase.WantError) 230 testutil.AssertStringContains(t, stdout.String(), testcase.WantOutput) 231 }) 232 } 233 } 234 235 func TestNewRelicList(t *testing.T) { 236 args := testutil.Args 237 scenarios := []testutil.TestScenario{ 238 { 239 Name: "validate missing --version flag", 240 Args: args("logging newrelic list"), 241 WantError: "error parsing arguments: required flag --version not provided", 242 }, 243 { 244 Name: "validate missing --service-id flag", 245 Args: args("logging newrelic list --version 3"), 246 WantError: "error reading service: no service ID found", 247 }, 248 { 249 Name: "validate ListNewRelics API error", 250 API: mock.API{ 251 ListVersionsFn: testutil.ListVersions, 252 ListNewRelicFn: func(i *fastly.ListNewRelicInput) ([]*fastly.NewRelic, error) { 253 return nil, testutil.Err 254 }, 255 }, 256 Args: args("logging newrelic list --service-id 123 --version 3"), 257 WantError: testutil.Err.Error(), 258 }, 259 { 260 Name: "validate ListNewRelics API success", 261 API: mock.API{ 262 ListVersionsFn: testutil.ListVersions, 263 ListNewRelicFn: listNewRelic, 264 }, 265 Args: args("logging newrelic list --service-id 123 --version 3"), 266 WantOutput: "SERVICE ID VERSION NAME\n123 3 foo\n123 3 bar\n", 267 }, 268 { 269 Name: "validate missing --autoclone flag is OK", 270 API: mock.API{ 271 ListVersionsFn: testutil.ListVersions, 272 ListNewRelicFn: listNewRelic, 273 }, 274 Args: args("logging newrelic list --service-id 123 --version 1"), 275 WantOutput: "SERVICE ID VERSION NAME\n123 1 foo\n123 1 bar\n", 276 }, 277 { 278 Name: "validate missing --verbose flag", 279 API: mock.API{ 280 ListVersionsFn: testutil.ListVersions, 281 ListNewRelicFn: listNewRelic, 282 }, 283 Args: args("logging newrelic list --service-id 123 --verbose --version 1"), 284 WantOutput: "Fastly API endpoint: https://api.fastly.com\nFastly API token provided via config file (profile: user)\n\nService ID (via --service-id): 123\n\nService Version: 1\n\nName: foo\n\nToken: \n\nFormat: \n\nFormat Version: 0\n\nPlacement: \n\nRegion: \n\nResponse Condition: \n\nCreated at: 2021-06-15 23:00:00 +0000 UTC\nUpdated at: 2021-06-15 23:00:00 +0000 UTC\nDeleted at: 2021-06-15 23:00:00 +0000 UTC\n\nName: bar\n\nToken: \n\nFormat: \n\nFormat Version: 0\n\nPlacement: \n\nRegion: \n\nResponse Condition: \n\nCreated at: 2021-06-15 23:00:00 +0000 UTC\nUpdated at: 2021-06-15 23:00:00 +0000 UTC\nDeleted at: 2021-06-15 23:00:00 +0000 UTC\n", 285 }, 286 } 287 288 for testcaseIdx := range scenarios { 289 testcase := &scenarios[testcaseIdx] 290 t.Run(testcase.Name, func(t *testing.T) { 291 var stdout bytes.Buffer 292 app.Init = func(_ []string, _ io.Reader) (*global.Data, error) { 293 opts := testutil.MockGlobalData(testcase.Args, &stdout) 294 opts.APIClientFactory = mock.APIClient(testcase.API) 295 return opts, nil 296 } 297 err := app.Run(testcase.Args, nil) 298 testutil.AssertErrorContains(t, err, testcase.WantError) 299 testutil.AssertStringContains(t, stdout.String(), testcase.WantOutput) 300 }) 301 } 302 } 303 304 func TestNewRelicUpdate(t *testing.T) { 305 args := testutil.Args 306 scenarios := []testutil.TestScenario{ 307 { 308 Name: "validate missing --name flag", 309 Args: args("logging newrelic update --service-id 123 --version 3"), 310 WantError: "error parsing arguments: required flag --name not provided", 311 }, 312 { 313 Name: "validate missing --version flag", 314 Args: args("logging newrelic update --name foobar --service-id 123"), 315 WantError: "error parsing arguments: required flag --version not provided", 316 }, 317 { 318 Name: "validate missing --service-id flag", 319 Args: args("logging newrelic update --name foobar --version 3"), 320 WantError: "error reading service: no service ID found", 321 }, 322 { 323 Name: "validate missing --autoclone flag", 324 API: mock.API{ 325 ListVersionsFn: testutil.ListVersions, 326 }, 327 Args: args("logging newrelic update --name foobar --service-id 123 --version 1"), 328 WantError: "service version 1 is not editable", 329 }, 330 { 331 Name: "validate UpdateNewRelic API error", 332 API: mock.API{ 333 ListVersionsFn: testutil.ListVersions, 334 UpdateNewRelicFn: func(i *fastly.UpdateNewRelicInput) (*fastly.NewRelic, error) { 335 return nil, testutil.Err 336 }, 337 }, 338 Args: args("logging newrelic update --name foobar --new-name beepboop --service-id 123 --version 3"), 339 WantError: testutil.Err.Error(), 340 }, 341 { 342 Name: "validate UpdateNewRelic API success", 343 API: mock.API{ 344 ListVersionsFn: testutil.ListVersions, 345 UpdateNewRelicFn: func(i *fastly.UpdateNewRelicInput) (*fastly.NewRelic, error) { 346 return &fastly.NewRelic{ 347 Name: i.NewName, 348 ServiceID: fastly.ToPointer(i.ServiceID), 349 ServiceVersion: fastly.ToPointer(i.ServiceVersion), 350 }, nil 351 }, 352 }, 353 Args: args("logging newrelic update --name foobar --new-name beepboop --service-id 123 --version 3"), 354 WantOutput: "Updated New Relic logging endpoint 'beepboop' (previously: foobar, service: 123, version: 3)", 355 }, 356 { 357 Name: "validate --autoclone results in cloned service version", 358 API: mock.API{ 359 ListVersionsFn: testutil.ListVersions, 360 CloneVersionFn: testutil.CloneVersionResult(4), 361 UpdateNewRelicFn: func(i *fastly.UpdateNewRelicInput) (*fastly.NewRelic, error) { 362 return &fastly.NewRelic{ 363 Name: i.NewName, 364 ServiceID: fastly.ToPointer(i.ServiceID), 365 ServiceVersion: fastly.ToPointer(i.ServiceVersion), 366 }, nil 367 }, 368 }, 369 Args: args("logging newrelic update --autoclone --name foobar --new-name beepboop --service-id 123 --version 1"), 370 WantOutput: "Updated New Relic logging endpoint 'beepboop' (previously: foobar, service: 123, version: 4)", 371 }, 372 } 373 374 for testcaseIdx := range scenarios { 375 testcase := &scenarios[testcaseIdx] 376 t.Run(testcase.Name, func(t *testing.T) { 377 var stdout bytes.Buffer 378 app.Init = func(_ []string, _ io.Reader) (*global.Data, error) { 379 opts := testutil.MockGlobalData(testcase.Args, &stdout) 380 opts.APIClientFactory = mock.APIClient(testcase.API) 381 return opts, nil 382 } 383 err := app.Run(testcase.Args, nil) 384 testutil.AssertErrorContains(t, err, testcase.WantError) 385 testutil.AssertStringContains(t, stdout.String(), testcase.WantOutput) 386 }) 387 } 388 } 389 390 func getNewRelic(i *fastly.GetNewRelicInput) (*fastly.NewRelic, error) { 391 t := testutil.Date 392 393 return &fastly.NewRelic{ 394 Name: fastly.ToPointer(i.Name), 395 Token: fastly.ToPointer("abc"), 396 ServiceID: fastly.ToPointer(i.ServiceID), 397 ServiceVersion: fastly.ToPointer(i.ServiceVersion), 398 399 CreatedAt: &t, 400 DeletedAt: &t, 401 UpdatedAt: &t, 402 }, nil 403 } 404 405 func listNewRelic(i *fastly.ListNewRelicInput) ([]*fastly.NewRelic, error) { 406 t := testutil.Date 407 vs := []*fastly.NewRelic{ 408 { 409 Name: fastly.ToPointer("foo"), 410 ServiceID: fastly.ToPointer(i.ServiceID), 411 ServiceVersion: fastly.ToPointer(i.ServiceVersion), 412 413 CreatedAt: &t, 414 DeletedAt: &t, 415 UpdatedAt: &t, 416 }, 417 { 418 Name: fastly.ToPointer("bar"), 419 ServiceID: fastly.ToPointer(i.ServiceID), 420 ServiceVersion: fastly.ToPointer(i.ServiceVersion), 421 422 CreatedAt: &t, 423 DeletedAt: &t, 424 UpdatedAt: &t, 425 }, 426 } 427 return vs, nil 428 }