github.com/kunnos/engine@v1.13.1/daemon/logger/awslogs/cloudwatchlogs_test.go (about) 1 package awslogs 2 3 import ( 4 "errors" 5 "fmt" 6 "net/http" 7 "reflect" 8 "runtime" 9 "strings" 10 "testing" 11 "time" 12 13 "github.com/aws/aws-sdk-go/aws" 14 "github.com/aws/aws-sdk-go/aws/awserr" 15 "github.com/aws/aws-sdk-go/aws/request" 16 "github.com/aws/aws-sdk-go/service/cloudwatchlogs" 17 "github.com/docker/docker/daemon/logger" 18 "github.com/docker/docker/daemon/logger/loggerutils" 19 "github.com/docker/docker/dockerversion" 20 ) 21 22 const ( 23 groupName = "groupName" 24 streamName = "streamName" 25 sequenceToken = "sequenceToken" 26 nextSequenceToken = "nextSequenceToken" 27 logline = "this is a log line" 28 ) 29 30 func TestNewAWSLogsClientUserAgentHandler(t *testing.T) { 31 ctx := logger.Context{ 32 Config: map[string]string{ 33 regionKey: "us-east-1", 34 }, 35 } 36 37 client, err := newAWSLogsClient(ctx) 38 if err != nil { 39 t.Fatal(err) 40 } 41 realClient, ok := client.(*cloudwatchlogs.CloudWatchLogs) 42 if !ok { 43 t.Fatal("Could not cast client to cloudwatchlogs.CloudWatchLogs") 44 } 45 buildHandlerList := realClient.Handlers.Build 46 request := &request.Request{ 47 HTTPRequest: &http.Request{ 48 Header: http.Header{}, 49 }, 50 } 51 buildHandlerList.Run(request) 52 expectedUserAgentString := fmt.Sprintf("Docker %s (%s) %s/%s (%s; %s; %s)", 53 dockerversion.Version, runtime.GOOS, aws.SDKName, aws.SDKVersion, runtime.Version(), runtime.GOOS, runtime.GOARCH) 54 userAgent := request.HTTPRequest.Header.Get("User-Agent") 55 if userAgent != expectedUserAgentString { 56 t.Errorf("Wrong User-Agent string, expected \"%s\" but was \"%s\"", 57 expectedUserAgentString, userAgent) 58 } 59 } 60 61 func TestNewAWSLogsClientRegionDetect(t *testing.T) { 62 ctx := logger.Context{ 63 Config: map[string]string{}, 64 } 65 66 mockMetadata := newMockMetadataClient() 67 newRegionFinder = func() regionFinder { 68 return mockMetadata 69 } 70 mockMetadata.regionResult <- ®ionResult{ 71 successResult: "us-east-1", 72 } 73 74 _, err := newAWSLogsClient(ctx) 75 if err != nil { 76 t.Fatal(err) 77 } 78 } 79 80 func TestCreateSuccess(t *testing.T) { 81 mockClient := newMockClient() 82 stream := &logStream{ 83 client: mockClient, 84 logGroupName: groupName, 85 logStreamName: streamName, 86 } 87 mockClient.createLogStreamResult <- &createLogStreamResult{} 88 89 err := stream.create() 90 91 if err != nil { 92 t.Errorf("Received unexpected err: %v\n", err) 93 } 94 argument := <-mockClient.createLogStreamArgument 95 if argument.LogGroupName == nil { 96 t.Fatal("Expected non-nil LogGroupName") 97 } 98 if *argument.LogGroupName != groupName { 99 t.Errorf("Expected LogGroupName to be %s", groupName) 100 } 101 if argument.LogStreamName == nil { 102 t.Fatal("Expected non-nil LogGroupName") 103 } 104 if *argument.LogStreamName != streamName { 105 t.Errorf("Expected LogStreamName to be %s", streamName) 106 } 107 } 108 109 func TestCreateError(t *testing.T) { 110 mockClient := newMockClient() 111 stream := &logStream{ 112 client: mockClient, 113 } 114 mockClient.createLogStreamResult <- &createLogStreamResult{ 115 errorResult: errors.New("Error!"), 116 } 117 118 err := stream.create() 119 120 if err == nil { 121 t.Fatal("Expected non-nil err") 122 } 123 } 124 125 func TestCreateAlreadyExists(t *testing.T) { 126 mockClient := newMockClient() 127 stream := &logStream{ 128 client: mockClient, 129 } 130 mockClient.createLogStreamResult <- &createLogStreamResult{ 131 errorResult: awserr.New(resourceAlreadyExistsCode, "", nil), 132 } 133 134 err := stream.create() 135 136 if err != nil { 137 t.Fatal("Expected nil err") 138 } 139 } 140 141 func TestPublishBatchSuccess(t *testing.T) { 142 mockClient := newMockClient() 143 stream := &logStream{ 144 client: mockClient, 145 logGroupName: groupName, 146 logStreamName: streamName, 147 sequenceToken: aws.String(sequenceToken), 148 } 149 mockClient.putLogEventsResult <- &putLogEventsResult{ 150 successResult: &cloudwatchlogs.PutLogEventsOutput{ 151 NextSequenceToken: aws.String(nextSequenceToken), 152 }, 153 } 154 events := []wrappedEvent{ 155 { 156 inputLogEvent: &cloudwatchlogs.InputLogEvent{ 157 Message: aws.String(logline), 158 }, 159 }, 160 } 161 162 stream.publishBatch(events) 163 if stream.sequenceToken == nil { 164 t.Fatal("Expected non-nil sequenceToken") 165 } 166 if *stream.sequenceToken != nextSequenceToken { 167 t.Errorf("Expected sequenceToken to be %s, but was %s", nextSequenceToken, *stream.sequenceToken) 168 } 169 argument := <-mockClient.putLogEventsArgument 170 if argument == nil { 171 t.Fatal("Expected non-nil PutLogEventsInput") 172 } 173 if argument.SequenceToken == nil { 174 t.Fatal("Expected non-nil PutLogEventsInput.SequenceToken") 175 } 176 if *argument.SequenceToken != sequenceToken { 177 t.Errorf("Expected PutLogEventsInput.SequenceToken to be %s, but was %s", sequenceToken, *argument.SequenceToken) 178 } 179 if len(argument.LogEvents) != 1 { 180 t.Errorf("Expected LogEvents to contain 1 element, but contains %d", len(argument.LogEvents)) 181 } 182 if argument.LogEvents[0] != events[0].inputLogEvent { 183 t.Error("Expected event to equal input") 184 } 185 } 186 187 func TestPublishBatchError(t *testing.T) { 188 mockClient := newMockClient() 189 stream := &logStream{ 190 client: mockClient, 191 logGroupName: groupName, 192 logStreamName: streamName, 193 sequenceToken: aws.String(sequenceToken), 194 } 195 mockClient.putLogEventsResult <- &putLogEventsResult{ 196 errorResult: errors.New("Error!"), 197 } 198 199 events := []wrappedEvent{ 200 { 201 inputLogEvent: &cloudwatchlogs.InputLogEvent{ 202 Message: aws.String(logline), 203 }, 204 }, 205 } 206 207 stream.publishBatch(events) 208 if stream.sequenceToken == nil { 209 t.Fatal("Expected non-nil sequenceToken") 210 } 211 if *stream.sequenceToken != sequenceToken { 212 t.Errorf("Expected sequenceToken to be %s, but was %s", sequenceToken, *stream.sequenceToken) 213 } 214 } 215 216 func TestPublishBatchInvalidSeqSuccess(t *testing.T) { 217 mockClient := newMockClientBuffered(2) 218 stream := &logStream{ 219 client: mockClient, 220 logGroupName: groupName, 221 logStreamName: streamName, 222 sequenceToken: aws.String(sequenceToken), 223 } 224 mockClient.putLogEventsResult <- &putLogEventsResult{ 225 errorResult: awserr.New(invalidSequenceTokenCode, "use token token", nil), 226 } 227 mockClient.putLogEventsResult <- &putLogEventsResult{ 228 successResult: &cloudwatchlogs.PutLogEventsOutput{ 229 NextSequenceToken: aws.String(nextSequenceToken), 230 }, 231 } 232 233 events := []wrappedEvent{ 234 { 235 inputLogEvent: &cloudwatchlogs.InputLogEvent{ 236 Message: aws.String(logline), 237 }, 238 }, 239 } 240 241 stream.publishBatch(events) 242 if stream.sequenceToken == nil { 243 t.Fatal("Expected non-nil sequenceToken") 244 } 245 if *stream.sequenceToken != nextSequenceToken { 246 t.Errorf("Expected sequenceToken to be %s, but was %s", nextSequenceToken, *stream.sequenceToken) 247 } 248 249 argument := <-mockClient.putLogEventsArgument 250 if argument == nil { 251 t.Fatal("Expected non-nil PutLogEventsInput") 252 } 253 if argument.SequenceToken == nil { 254 t.Fatal("Expected non-nil PutLogEventsInput.SequenceToken") 255 } 256 if *argument.SequenceToken != sequenceToken { 257 t.Errorf("Expected PutLogEventsInput.SequenceToken to be %s, but was %s", sequenceToken, *argument.SequenceToken) 258 } 259 if len(argument.LogEvents) != 1 { 260 t.Errorf("Expected LogEvents to contain 1 element, but contains %d", len(argument.LogEvents)) 261 } 262 if argument.LogEvents[0] != events[0].inputLogEvent { 263 t.Error("Expected event to equal input") 264 } 265 266 argument = <-mockClient.putLogEventsArgument 267 if argument == nil { 268 t.Fatal("Expected non-nil PutLogEventsInput") 269 } 270 if argument.SequenceToken == nil { 271 t.Fatal("Expected non-nil PutLogEventsInput.SequenceToken") 272 } 273 if *argument.SequenceToken != "token" { 274 t.Errorf("Expected PutLogEventsInput.SequenceToken to be %s, but was %s", "token", *argument.SequenceToken) 275 } 276 if len(argument.LogEvents) != 1 { 277 t.Errorf("Expected LogEvents to contain 1 element, but contains %d", len(argument.LogEvents)) 278 } 279 if argument.LogEvents[0] != events[0].inputLogEvent { 280 t.Error("Expected event to equal input") 281 } 282 } 283 284 func TestPublishBatchAlreadyAccepted(t *testing.T) { 285 mockClient := newMockClient() 286 stream := &logStream{ 287 client: mockClient, 288 logGroupName: groupName, 289 logStreamName: streamName, 290 sequenceToken: aws.String(sequenceToken), 291 } 292 mockClient.putLogEventsResult <- &putLogEventsResult{ 293 errorResult: awserr.New(dataAlreadyAcceptedCode, "use token token", nil), 294 } 295 296 events := []wrappedEvent{ 297 { 298 inputLogEvent: &cloudwatchlogs.InputLogEvent{ 299 Message: aws.String(logline), 300 }, 301 }, 302 } 303 304 stream.publishBatch(events) 305 if stream.sequenceToken == nil { 306 t.Fatal("Expected non-nil sequenceToken") 307 } 308 if *stream.sequenceToken != "token" { 309 t.Errorf("Expected sequenceToken to be %s, but was %s", "token", *stream.sequenceToken) 310 } 311 312 argument := <-mockClient.putLogEventsArgument 313 if argument == nil { 314 t.Fatal("Expected non-nil PutLogEventsInput") 315 } 316 if argument.SequenceToken == nil { 317 t.Fatal("Expected non-nil PutLogEventsInput.SequenceToken") 318 } 319 if *argument.SequenceToken != sequenceToken { 320 t.Errorf("Expected PutLogEventsInput.SequenceToken to be %s, but was %s", sequenceToken, *argument.SequenceToken) 321 } 322 if len(argument.LogEvents) != 1 { 323 t.Errorf("Expected LogEvents to contain 1 element, but contains %d", len(argument.LogEvents)) 324 } 325 if argument.LogEvents[0] != events[0].inputLogEvent { 326 t.Error("Expected event to equal input") 327 } 328 } 329 330 func TestCollectBatchSimple(t *testing.T) { 331 mockClient := newMockClient() 332 stream := &logStream{ 333 client: mockClient, 334 logGroupName: groupName, 335 logStreamName: streamName, 336 sequenceToken: aws.String(sequenceToken), 337 messages: make(chan *logger.Message), 338 } 339 mockClient.putLogEventsResult <- &putLogEventsResult{ 340 successResult: &cloudwatchlogs.PutLogEventsOutput{ 341 NextSequenceToken: aws.String(nextSequenceToken), 342 }, 343 } 344 ticks := make(chan time.Time) 345 newTicker = func(_ time.Duration) *time.Ticker { 346 return &time.Ticker{ 347 C: ticks, 348 } 349 } 350 351 go stream.collectBatch() 352 353 stream.Log(&logger.Message{ 354 Line: []byte(logline), 355 Timestamp: time.Time{}, 356 }) 357 358 ticks <- time.Time{} 359 stream.Close() 360 361 argument := <-mockClient.putLogEventsArgument 362 if argument == nil { 363 t.Fatal("Expected non-nil PutLogEventsInput") 364 } 365 if len(argument.LogEvents) != 1 { 366 t.Errorf("Expected LogEvents to contain 1 element, but contains %d", len(argument.LogEvents)) 367 } 368 if *argument.LogEvents[0].Message != logline { 369 t.Errorf("Expected message to be %s but was %s", logline, *argument.LogEvents[0].Message) 370 } 371 } 372 373 func TestCollectBatchTicker(t *testing.T) { 374 mockClient := newMockClient() 375 stream := &logStream{ 376 client: mockClient, 377 logGroupName: groupName, 378 logStreamName: streamName, 379 sequenceToken: aws.String(sequenceToken), 380 messages: make(chan *logger.Message), 381 } 382 mockClient.putLogEventsResult <- &putLogEventsResult{ 383 successResult: &cloudwatchlogs.PutLogEventsOutput{ 384 NextSequenceToken: aws.String(nextSequenceToken), 385 }, 386 } 387 ticks := make(chan time.Time) 388 newTicker = func(_ time.Duration) *time.Ticker { 389 return &time.Ticker{ 390 C: ticks, 391 } 392 } 393 394 go stream.collectBatch() 395 396 stream.Log(&logger.Message{ 397 Line: []byte(logline + " 1"), 398 Timestamp: time.Time{}, 399 }) 400 stream.Log(&logger.Message{ 401 Line: []byte(logline + " 2"), 402 Timestamp: time.Time{}, 403 }) 404 405 ticks <- time.Time{} 406 407 // Verify first batch 408 argument := <-mockClient.putLogEventsArgument 409 if argument == nil { 410 t.Fatal("Expected non-nil PutLogEventsInput") 411 } 412 if len(argument.LogEvents) != 2 { 413 t.Errorf("Expected LogEvents to contain 2 elements, but contains %d", len(argument.LogEvents)) 414 } 415 if *argument.LogEvents[0].Message != logline+" 1" { 416 t.Errorf("Expected message to be %s but was %s", logline+" 1", *argument.LogEvents[0].Message) 417 } 418 if *argument.LogEvents[1].Message != logline+" 2" { 419 t.Errorf("Expected message to be %s but was %s", logline+" 2", *argument.LogEvents[0].Message) 420 } 421 422 stream.Log(&logger.Message{ 423 Line: []byte(logline + " 3"), 424 Timestamp: time.Time{}, 425 }) 426 427 ticks <- time.Time{} 428 argument = <-mockClient.putLogEventsArgument 429 if argument == nil { 430 t.Fatal("Expected non-nil PutLogEventsInput") 431 } 432 if len(argument.LogEvents) != 1 { 433 t.Errorf("Expected LogEvents to contain 1 elements, but contains %d", len(argument.LogEvents)) 434 } 435 if *argument.LogEvents[0].Message != logline+" 3" { 436 t.Errorf("Expected message to be %s but was %s", logline+" 3", *argument.LogEvents[0].Message) 437 } 438 439 stream.Close() 440 441 } 442 443 func TestCollectBatchClose(t *testing.T) { 444 mockClient := newMockClient() 445 stream := &logStream{ 446 client: mockClient, 447 logGroupName: groupName, 448 logStreamName: streamName, 449 sequenceToken: aws.String(sequenceToken), 450 messages: make(chan *logger.Message), 451 } 452 mockClient.putLogEventsResult <- &putLogEventsResult{ 453 successResult: &cloudwatchlogs.PutLogEventsOutput{ 454 NextSequenceToken: aws.String(nextSequenceToken), 455 }, 456 } 457 var ticks = make(chan time.Time) 458 newTicker = func(_ time.Duration) *time.Ticker { 459 return &time.Ticker{ 460 C: ticks, 461 } 462 } 463 464 go stream.collectBatch() 465 466 stream.Log(&logger.Message{ 467 Line: []byte(logline), 468 Timestamp: time.Time{}, 469 }) 470 471 // no ticks 472 stream.Close() 473 474 argument := <-mockClient.putLogEventsArgument 475 if argument == nil { 476 t.Fatal("Expected non-nil PutLogEventsInput") 477 } 478 if len(argument.LogEvents) != 1 { 479 t.Errorf("Expected LogEvents to contain 1 element, but contains %d", len(argument.LogEvents)) 480 } 481 if *argument.LogEvents[0].Message != logline { 482 t.Errorf("Expected message to be %s but was %s", logline, *argument.LogEvents[0].Message) 483 } 484 } 485 486 func TestCollectBatchLineSplit(t *testing.T) { 487 mockClient := newMockClient() 488 stream := &logStream{ 489 client: mockClient, 490 logGroupName: groupName, 491 logStreamName: streamName, 492 sequenceToken: aws.String(sequenceToken), 493 messages: make(chan *logger.Message), 494 } 495 mockClient.putLogEventsResult <- &putLogEventsResult{ 496 successResult: &cloudwatchlogs.PutLogEventsOutput{ 497 NextSequenceToken: aws.String(nextSequenceToken), 498 }, 499 } 500 var ticks = make(chan time.Time) 501 newTicker = func(_ time.Duration) *time.Ticker { 502 return &time.Ticker{ 503 C: ticks, 504 } 505 } 506 507 go stream.collectBatch() 508 509 longline := strings.Repeat("A", maximumBytesPerEvent) 510 stream.Log(&logger.Message{ 511 Line: []byte(longline + "B"), 512 Timestamp: time.Time{}, 513 }) 514 515 // no ticks 516 stream.Close() 517 518 argument := <-mockClient.putLogEventsArgument 519 if argument == nil { 520 t.Fatal("Expected non-nil PutLogEventsInput") 521 } 522 if len(argument.LogEvents) != 2 { 523 t.Errorf("Expected LogEvents to contain 2 elements, but contains %d", len(argument.LogEvents)) 524 } 525 if *argument.LogEvents[0].Message != longline { 526 t.Errorf("Expected message to be %s but was %s", longline, *argument.LogEvents[0].Message) 527 } 528 if *argument.LogEvents[1].Message != "B" { 529 t.Errorf("Expected message to be %s but was %s", "B", *argument.LogEvents[1].Message) 530 } 531 } 532 533 func TestCollectBatchMaxEvents(t *testing.T) { 534 mockClient := newMockClientBuffered(1) 535 stream := &logStream{ 536 client: mockClient, 537 logGroupName: groupName, 538 logStreamName: streamName, 539 sequenceToken: aws.String(sequenceToken), 540 messages: make(chan *logger.Message), 541 } 542 mockClient.putLogEventsResult <- &putLogEventsResult{ 543 successResult: &cloudwatchlogs.PutLogEventsOutput{ 544 NextSequenceToken: aws.String(nextSequenceToken), 545 }, 546 } 547 var ticks = make(chan time.Time) 548 newTicker = func(_ time.Duration) *time.Ticker { 549 return &time.Ticker{ 550 C: ticks, 551 } 552 } 553 554 go stream.collectBatch() 555 556 line := "A" 557 for i := 0; i <= maximumLogEventsPerPut; i++ { 558 stream.Log(&logger.Message{ 559 Line: []byte(line), 560 Timestamp: time.Time{}, 561 }) 562 } 563 564 // no ticks 565 stream.Close() 566 567 argument := <-mockClient.putLogEventsArgument 568 if argument == nil { 569 t.Fatal("Expected non-nil PutLogEventsInput") 570 } 571 if len(argument.LogEvents) != maximumLogEventsPerPut { 572 t.Errorf("Expected LogEvents to contain %d elements, but contains %d", maximumLogEventsPerPut, len(argument.LogEvents)) 573 } 574 575 argument = <-mockClient.putLogEventsArgument 576 if argument == nil { 577 t.Fatal("Expected non-nil PutLogEventsInput") 578 } 579 if len(argument.LogEvents) != 1 { 580 t.Errorf("Expected LogEvents to contain %d elements, but contains %d", 1, len(argument.LogEvents)) 581 } 582 } 583 584 func TestCollectBatchMaxTotalBytes(t *testing.T) { 585 mockClient := newMockClientBuffered(1) 586 stream := &logStream{ 587 client: mockClient, 588 logGroupName: groupName, 589 logStreamName: streamName, 590 sequenceToken: aws.String(sequenceToken), 591 messages: make(chan *logger.Message), 592 } 593 mockClient.putLogEventsResult <- &putLogEventsResult{ 594 successResult: &cloudwatchlogs.PutLogEventsOutput{ 595 NextSequenceToken: aws.String(nextSequenceToken), 596 }, 597 } 598 var ticks = make(chan time.Time) 599 newTicker = func(_ time.Duration) *time.Ticker { 600 return &time.Ticker{ 601 C: ticks, 602 } 603 } 604 605 go stream.collectBatch() 606 607 longline := strings.Repeat("A", maximumBytesPerPut) 608 stream.Log(&logger.Message{ 609 Line: []byte(longline + "B"), 610 Timestamp: time.Time{}, 611 }) 612 613 // no ticks 614 stream.Close() 615 616 argument := <-mockClient.putLogEventsArgument 617 if argument == nil { 618 t.Fatal("Expected non-nil PutLogEventsInput") 619 } 620 bytes := 0 621 for _, event := range argument.LogEvents { 622 bytes += len(*event.Message) 623 } 624 if bytes > maximumBytesPerPut { 625 t.Errorf("Expected <= %d bytes but was %d", maximumBytesPerPut, bytes) 626 } 627 628 argument = <-mockClient.putLogEventsArgument 629 if len(argument.LogEvents) != 1 { 630 t.Errorf("Expected LogEvents to contain 1 elements, but contains %d", len(argument.LogEvents)) 631 } 632 message := *argument.LogEvents[0].Message 633 if message[len(message)-1:] != "B" { 634 t.Errorf("Expected message to be %s but was %s", "B", message[len(message)-1:]) 635 } 636 } 637 638 func TestCollectBatchWithDuplicateTimestamps(t *testing.T) { 639 mockClient := newMockClient() 640 stream := &logStream{ 641 client: mockClient, 642 logGroupName: groupName, 643 logStreamName: streamName, 644 sequenceToken: aws.String(sequenceToken), 645 messages: make(chan *logger.Message), 646 } 647 mockClient.putLogEventsResult <- &putLogEventsResult{ 648 successResult: &cloudwatchlogs.PutLogEventsOutput{ 649 NextSequenceToken: aws.String(nextSequenceToken), 650 }, 651 } 652 ticks := make(chan time.Time) 653 newTicker = func(_ time.Duration) *time.Ticker { 654 return &time.Ticker{ 655 C: ticks, 656 } 657 } 658 659 go stream.collectBatch() 660 661 times := maximumLogEventsPerPut 662 expectedEvents := []*cloudwatchlogs.InputLogEvent{} 663 timestamp := time.Now() 664 for i := 0; i < times; i++ { 665 line := fmt.Sprintf("%d", i) 666 if i%2 == 0 { 667 timestamp.Add(1 * time.Nanosecond) 668 } 669 stream.Log(&logger.Message{ 670 Line: []byte(line), 671 Timestamp: timestamp, 672 }) 673 expectedEvents = append(expectedEvents, &cloudwatchlogs.InputLogEvent{ 674 Message: aws.String(line), 675 Timestamp: aws.Int64(timestamp.UnixNano() / int64(time.Millisecond)), 676 }) 677 } 678 679 ticks <- time.Time{} 680 stream.Close() 681 682 argument := <-mockClient.putLogEventsArgument 683 if argument == nil { 684 t.Fatal("Expected non-nil PutLogEventsInput") 685 } 686 if len(argument.LogEvents) != times { 687 t.Errorf("Expected LogEvents to contain %d elements, but contains %d", times, len(argument.LogEvents)) 688 } 689 for i := 0; i < times; i++ { 690 if !reflect.DeepEqual(*argument.LogEvents[i], *expectedEvents[i]) { 691 t.Errorf("Expected event to be %v but was %v", *expectedEvents[i], *argument.LogEvents[i]) 692 } 693 } 694 } 695 696 func TestCreateTagSuccess(t *testing.T) { 697 mockClient := newMockClient() 698 ctx := logger.Context{ 699 ContainerName: "/test-container", 700 ContainerID: "container-abcdefghijklmnopqrstuvwxyz01234567890", 701 Config: map[string]string{"tag": "{{.Name}}/{{.FullID}}"}, 702 } 703 logStreamName, e := loggerutils.ParseLogTag(ctx, loggerutils.DefaultTemplate) 704 if e != nil { 705 t.Errorf("Error generating tag: %q", e) 706 } 707 stream := &logStream{ 708 client: mockClient, 709 logGroupName: groupName, 710 logStreamName: logStreamName, 711 } 712 mockClient.createLogStreamResult <- &createLogStreamResult{} 713 714 err := stream.create() 715 716 if err != nil { 717 t.Errorf("Received unexpected err: %v\n", err) 718 } 719 argument := <-mockClient.createLogStreamArgument 720 721 if *argument.LogStreamName != "test-container/container-abcdefghijklmnopqrstuvwxyz01234567890" { 722 t.Errorf("Expected LogStreamName to be %s", "test-container/container-abcdefghijklmnopqrstuvwxyz01234567890") 723 } 724 }