Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
76 commits
Select commit Hold shift + click to select a range
4f42cef
feat(e2e): Add comprehensive ECS E2E testing infrastructure and test …
JLineaweaver Dec 10, 2025
3c00ebc
fix(e2e): Use correct TaskDefinitionVolume types for ECS apps
JLineaweaver Dec 10, 2025
9c65a28
refactor(e2e): Consolidate ECS tests into dedicated ecs/ folder
JLineaweaver Dec 10, 2025
05e3f4c
fix(e2e): Fix syntax errors in ECS test provisioner setup
JLineaweaver Dec 10, 2025
e006957
docs(releasenotes): Add release note for comprehensive ECS E2E testin…
JLineaweaver Dec 10, 2025
fdac5e2
docs: Update team ownership from containers/orchestrator to ecs-exper…
JLineaweaver Dec 10, 2025
5aae952
fix(e2e): Fix ECS test compilation errors
JLineaweaver Dec 10, 2025
2beff2b
refactor(e2e): Move test helpers to non-test files to fix import cycle
JLineaweaver Dec 10, 2025
8b6147a
fix(e2e): Refactor ECS tests to use helper functions for metrics/logs
JLineaweaver Dec 10, 2025
d0459c6
fix(e2e): Complete ECS test refactoring - replace private API calls w…
JLineaweaver Dec 10, 2025
f7f027c
docs(e2e): Update ECS README with current API methods
JLineaweaver Dec 10, 2025
96682c0
refactor(e2e): Move BaseSuite to ECS package and restore containers f…
JLineaweaver Dec 10, 2025
ed8a23e
refactor(e2e): Complete ECS test migration from containers to ecs pac…
JLineaweaver Dec 10, 2025
eb363fa
refactor(e2e): Apply Go code review fixes to ECS APM tests
JLineaweaver Dec 10, 2025
b3ddf58
fix(e2e): Remove unused imports from apm_test.go
JLineaweaver Dec 10, 2025
68bdc7c
fix(e2e): Fix linter issues in ECS and containers tests
JLineaweaver Dec 11, 2025
db0d1ae
ci(e2e): Add dedicated ECS test job and remove old TestECSSuite
JLineaweaver Dec 12, 2025
a247410
fix(e2e): Rename helper methods from Test* to Assert* to prevent test…
JLineaweaver Dec 12, 2025
e9094f7
fix(e2e): Add wait for ECS container instances before creating services
JLineaweaver Dec 12, 2025
72d99c9
fix(e2e): Increase ECS node group to 2 instances for static port mapp…
JLineaweaver Dec 12, 2025
194b80d
fix(e2e): Configure APM endpoint for FakeIntake in ECS tests
JLineaweaver Dec 12, 2025
1be4c44
fix(e2e): Configure primary metrics endpoint (DD_URL) for FakeIntake
JLineaweaver Dec 15, 2025
94a08cc
fix(e2e): Remove logs component telemetry check from readiness test
JLineaweaver Dec 15, 2025
5d05f92
feat(e2e): Add DD_SERVICE, DD_ENV, DD_VERSION to ECS workloads
JLineaweaver Dec 15, 2025
b50b494
fix(e2e): Remove component telemetry checks from managed instance hea…
JLineaweaver Dec 16, 2025
8e46b2d
Add Docker labels for service/env/version tagging on container metrics
JLineaweaver Dec 16, 2025
d0c7bd2
Add expected service/env/version tags to EC2 log tests
JLineaweaver Dec 16, 2025
f36395c
Fix gofmt formatting in checks_test.go
JLineaweaver Dec 17, 2025
050a956
fix(e2e): Update managed tests to use ECS task tags instead of host tags
JLineaweaver Dec 17, 2025
1d28ddf
fix(e2e): Fix nginx EC2 log collection test filter
JLineaweaver Dec 17, 2025
68d33f8
fix(e2e): Fix platform test failures in ECS tests
JLineaweaver Dec 17, 2025
2cd3d9d
fix(e2e): Add Docker labels to tracegen containers for ECS metadata t…
JLineaweaver Dec 18, 2025
6b5fdb1
fix(e2e): Correct APM test expectations for trace tags
JLineaweaver Dec 18, 2025
cca32a3
fix(e2e): Enable ECS metadata tagging for APM traces
JLineaweaver Dec 19, 2025
14117cb
fix(e2e): Remove invalid DD_APM_TAG_CARDINALITY setting
JLineaweaver Dec 19, 2025
f4624ed
fix(e2e): Enable APM container tag enrichment for ECS metadata tags o…
JLineaweaver Dec 19, 2025
10e1c78
fix(e2e): Correct environment variable name for container proc root
JLineaweaver Dec 19, 2025
a51f74e
Add debug logging to investigate APM trace enrichment
JLineaweaver Dec 22, 2025
e0c02b8
fix(e2e): Check TracerPayload.Tags for ECS container tags in APM tests
JLineaweaver Jan 12, 2026
163a6ad
Merge remote-tracking branch 'origin/main' into jlineaweaver/exp-133
JLineaweaver Jan 30, 2026
01be35e
ci: Add ECS e2e test suite to GitLab CI pipeline
JLineaweaver Jan 30, 2026
b357301
fix(e2e): Add Test00UpAndRunning warmup test to ECS test suites
JLineaweaver Jan 30, 2026
11fba4d
fix(e2e): Disable DD_APM_ENABLE_CONTAINER_TAGS_BUFFER for individual …
JLineaweaver Jan 31, 2026
371831d
fix(e2e): Correct trace-agent component metric prefix in APM health c…
JLineaweaver Feb 2, 2026
450ea33
fix(e2e): Remove ecs_launch_type assertion from managed instance test
JLineaweaver Feb 2, 2026
794db25
fix(e2e): Update APM tests to expect bundled container tags format
JLineaweaver Feb 4, 2026
623e943
fix(e2e): Fix regex patterns to match bundled container tags correctly
JLineaweaver Feb 4, 2026
06be637
fix(e2e): Revert APM trace tag patterns to match TracerPayload.Tags f…
JLineaweaver Feb 5, 2026
19baddf
fix(e2e): Use bundled tag format for APM trace validation
JLineaweaver Feb 5, 2026
cdd19ff
fix(e2e): Fix ECS APM tests to correctly validate bundled container tags
JLineaweaver Feb 6, 2026
7fe5fe1
fix(e2e): Improve bundled container tag pattern matching in ECS tests
JLineaweaver Feb 6, 2026
0bc8fcd
fix(e2e): Use '=' separator in bundled container tag patterns
JLineaweaver Feb 6, 2026
f957948
fix(e2e): Revert to ':' separator - base_helpers concatenates with k+…
JLineaweaver Feb 12, 2026
efbef83
debug(e2e): Add logging to see actual trace tags during matching
JLineaweaver Feb 12, 2026
ca83623
debug(e2e): Add logging to testTrace to debug pattern matching failures
JLineaweaver Feb 12, 2026
53f6d3b
fix(e2e): Use non-greedy regex to avoid matching cluster name in serv…
JLineaweaver Feb 13, 2026
e2fac6c
Merge branch 'main' into jlineaweaver/exp-133
JLineaweaver Feb 13, 2026
5fef8a5
fix(e2e): Fix ECS E2E test timeouts and CODEOWNERS lint failure
JLineaweaver Feb 17, 2026
503a989
Merge branch 'main' into jlineaweaver/exp-133
JLineaweaver Feb 18, 2026
ec9ea37
fix(e2e): Use container metrics for service/env tag validation
JLineaweaver Feb 18, 2026
eb92f02
fix(e2e): PR review cleanup - fix bugs, deduplicate, update README
JLineaweaver Feb 19, 2026
4cf2b35
fix(e2e): Fix gofmt formatting and remove dead helper code
JLineaweaver Feb 19, 2026
51229c7
fix(e2e): Deploy trace-correlated workloads and fix managed instance …
JLineaweaver Feb 20, 2026
1170e6b
fix(e2e): Enable trace-log correlation via tracegen DD_LOGS_INJECTION
JLineaweaver Feb 20, 2026
1b5d53b
fix(e2e): Remove trace-log correlation tests, fix managed trace tag l…
JLineaweaver Feb 23, 2026
a101205
Merge branch 'main' into jlineaweaver/exp-133
JLineaweaver Feb 23, 2026
9ac966c
Merge branch 'main' into jlineaweaver/exp-133
JLineaweaver Mar 4, 2026
1c7c5e4
Remove unused ECS test app components
JLineaweaver Mar 4, 2026
948dac1
Fix ECS README test counts and remove stale references
JLineaweaver Mar 4, 2026
c1529a8
Clean up hollow ECS E2E tests and restore infrastructure config
JLineaweaver Mar 4, 2026
454c331
Merge remote-tracking branch 'origin/main' into jlineaweaver/exp-133
JLineaweaver Mar 4, 2026
e8d76f5
Remove unused testCheckRun from containers base_test.go and tidy go.mod
JLineaweaver Mar 5, 2026
8dbee13
Merge branch 'main' into jlineaweaver/exp-133
JLineaweaver Mar 5, 2026
b493323
Merge branch 'main' into jlineaweaver/exp-133
JLineaweaver Mar 6, 2026
9df34af
Fix release note to match actual test suite state
JLineaweaver Mar 9, 2026
ac7c6ef
Address PR review feedback for ECS E2E infrastructure
JLineaweaver Mar 17, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/CODEOWNERS
Original file line number Diff line number Diff line change
Expand Up @@ -811,7 +811,7 @@
/test/new-e2e/tests/agent-subcommands/secret @DataDog/agent-configuration
/test/new-e2e/tests/agent-subcommands/status @DataDog/agent-configuration
/test/new-e2e/tests/containers @DataDog/container-integrations @DataDog/container-platform
/test/new-e2e/tests/containers/ecs_test.go @DataDog/ecs-experiences
/test/new-e2e/tests/ecs/ @DataDog/ecs-experiences
/test/new-e2e/tests/discovery @DataDog/agent-discovery
/test/new-e2e/tests/fips-compliance @DataDog/agent-runtimes
/test/new-e2e/tests/ha-agent @DataDog/ndm-core
Expand Down
23 changes: 23 additions & 0 deletions .gitlab/test/e2e/e2e.yml
Original file line number Diff line number Diff line change
Expand Up @@ -310,6 +310,29 @@ new-e2e-containers-eks:
ON_NIGHTLY_FIPS: "true"
retry: !reference [.retry_only_infra_failure, retry]

new-e2e-ecs:
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing retry directive on new-e2e-ecs. All peer jobs (new-e2e-containers-eks, new-e2e-containers-openshift, etc.) explicitly add retry: !reference [.retry_only_infra_failure, retry]. Without it, a single transient AWS failure permanently fails the job.

extends: .new_e2e_template
needs:
- !reference [.needs_new_e2e_template]
- qa_agent
- qa_agent_jmx
- qa_dca
- qa_dogstatsd
rules:
- !reference [.on_container_or_e2e_changes]
- !reference [.manual]
variables:
TARGETS: ./tests/ecs
TEAM: ecs-experiences
ON_NIGHTLY_FIPS: "true"
retry: !reference [.retry_only_infra_failure, retry]
parallel:
matrix:
- EXTRA_PARAMS: --run TestECSAPMSuite
- EXTRA_PARAMS: --run TestECSManagedSuite
- EXTRA_PARAMS: --run TestECSChecksSuite
- EXTRA_PARAMS: --run TestECSPlatformSuite

new-e2e-containers-openshift-init:
stage: e2e_init
extends: .new_e2e_template
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# Each section from every release note are combined when the
# CHANGELOG.rst is rendered. So the text needs to be worded so that
# it does not depend on any information only available in another
# section. This may mean repeating some details, but each section
# must be readable independently of the other.
#
# Each section note must be formatted as reStructuredText.
---
other:
- |
Migrated ECS E2E tests into a dedicated test/new-e2e/tests/ecs/ package
with 4 test suites (18 tests) covering APM/DogStatsD, check autodiscovery,
platform features, and managed instances. All tests validate specific
metrics, tags, and traces against regex patterns across Fargate, EC2,
and Managed Instance deployment types.
25 changes: 24 additions & 1 deletion test/e2e-framework/components/datadog/agent/ecs.go
Original file line number Diff line number Diff line change
Expand Up @@ -115,7 +115,22 @@ func ecsLinuxAgentSingleContainerDefinition(e config.Env, apiKeySSMParamName pul
Name: pulumi.StringPtr("DD_DOGSTATSD_ORIGIN_DETECTION_CLIENT"),
Value: pulumi.StringPtr("true"),
},

ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_APM_ENABLE_CONTAINER_TAGS_BUFFER"),
Value: pulumi.StringPtr("true"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_CONTAINER_PROC_ROOT"),
Value: pulumi.StringPtr("/host/proc"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_LOG_LEVEL"),
Value: pulumi.StringPtr("debug"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_APM_LOG_FILE"),
Value: pulumi.StringPtr("stdout"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_DOGSTATSD_SOCKET"),
Value: pulumi.StringPtr("/var/run/datadog/dsd.socket"),
Expand Down Expand Up @@ -253,6 +268,14 @@ func ecsFakeintakeAdditionalEndpointsEnv(fakeintake *fakeintake.Fakeintake) []ec
Name: pulumi.StringPtr("DD_REMOTE_CONFIGURATION_NO_TLS_VALIDATION"),
Value: pulumi.StringPtr("true"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_URL"),
Value: fakeintake.URL.ToStringOutput(),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_APM_DD_URL"),
Value: fakeintake.URL.ToStringOutput(),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_PROCESS_CONFIG_PROCESS_DD_URL"),
Value: fakeintake.URL.ToStringOutput(),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,13 @@ func FargateAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, apiK
Condition: pulumi.String("HEALTHY"),
},
},
PortMappings: ecs.TaskDefinitionPortMappingArray{},
PortMappings: ecs.TaskDefinitionPortMappingArray{
ecs.TaskDefinitionPortMappingArgs{
ContainerPort: pulumi.IntPtr(8080),
HostPort: pulumi.IntPtr(8080),
Protocol: pulumi.StringPtr("tcp"),
},
},
}

serverTaskDef, err := ecsClient.FargateWindowsTaskDefinitionWithAgent(e, "aspnet-fg-server", pulumi.String("aspnet-fg"), 4096, 8192, map[string]ecs.TaskDefinitionContainerDefinitionArgs{"aspnetsample": *serverContainer}, apiKeySSMParamName, fakeIntake, "", opts...)
Expand Down
19 changes: 18 additions & 1 deletion test/e2e-framework/components/datadog/apps/nginx/ecs.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,20 @@ func EcsAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, opts ...
"nginx": {
Name: pulumi.String("nginx"),
Image: pulumi.String("ghcr.io/datadog/apps-nginx-server:" + apps.Version),
Environment: ecs.TaskDefinitionKeyValuePairArray{
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_SERVICE"),
Value: pulumi.StringPtr("nginx"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_ENV"),
Value: pulumi.StringPtr("e2e-test"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_VERSION"),
Value: pulumi.StringPtr("1.0"),
},
},
DockerLabels: pulumi.StringMap{
"com.datadoghq.ad.checks": pulumi.String(utils.JSONMustMarshal(
map[string]interface{}{
Expand All @@ -51,7 +65,10 @@ func EcsAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, opts ...
},
},
)),
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:ec2\"]"),
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:ec2\"]"),
"com.datadoghq.tags.service": pulumi.String("nginx"),
"com.datadoghq.tags.env": pulumi.String("e2e-test"),
"com.datadoghq.tags.version": pulumi.String("1.0"),
},
Cpu: pulumi.IntPtr(100),
Memory: pulumi.IntPtr(96),
Expand Down
19 changes: 18 additions & 1 deletion test/e2e-framework/components/datadog/apps/nginx/ecsFargate.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,20 @@ func FargateAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, apiK
serverContainer := &ecs.TaskDefinitionContainerDefinitionArgs{
Name: pulumi.String("nginx"),
Image: pulumi.String("ghcr.io/datadog/apps-nginx-server:" + apps.Version),
Environment: ecs.TaskDefinitionKeyValuePairArray{
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_SERVICE"),
Value: pulumi.StringPtr("nginx-fargate"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_ENV"),
Value: pulumi.StringPtr("e2e-test"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_VERSION"),
Value: pulumi.StringPtr("1.0"),
},
},
DockerLabels: pulumi.StringMap{
"com.datadoghq.ad.checks": pulumi.String(utils.JSONMustMarshal(
map[string]interface{}{
Expand All @@ -46,7 +60,10 @@ func FargateAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, apiK
},
},
)),
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:fargate\"]"),
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:fargate\"]"),
"com.datadoghq.tags.service": pulumi.String("nginx-fargate"),
"com.datadoghq.tags.env": pulumi.String("e2e-test"),
"com.datadoghq.tags.version": pulumi.String("1.0"),
},
Cpu: pulumi.IntPtr(100),
Memory: pulumi.IntPtr(96),
Expand Down
19 changes: 18 additions & 1 deletion test/e2e-framework/components/datadog/apps/redis/ecs.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,8 +41,25 @@ func EcsAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, opts ...
"redis": {
Name: pulumi.String("redis"),
Image: pulumi.String("ghcr.io/datadog/redis:" + apps.Version),
Environment: ecs.TaskDefinitionKeyValuePairArray{
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_SERVICE"),
Value: pulumi.StringPtr("redis"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_ENV"),
Value: pulumi.StringPtr("e2e-test"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_VERSION"),
Value: pulumi.StringPtr("1.0"),
},
},
DockerLabels: pulumi.StringMap{
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:ec2\"]"),
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:ec2\"]"),
"com.datadoghq.tags.service": pulumi.String("redis"),
"com.datadoghq.tags.env": pulumi.String("e2e-test"),
"com.datadoghq.tags.version": pulumi.String("1.0"),
},
Command: pulumi.StringArray{
pulumi.String("--loglevel"),
Expand Down
19 changes: 18 additions & 1 deletion test/e2e-framework/components/datadog/apps/redis/ecsFargate.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,8 +35,25 @@ func FargateAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, apiK
serverContainer := &ecs.TaskDefinitionContainerDefinitionArgs{
Name: pulumi.String("redis"),
Image: pulumi.String("ghcr.io/datadog/redis:" + apps.Version),
Environment: ecs.TaskDefinitionKeyValuePairArray{
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_SERVICE"),
Value: pulumi.StringPtr("redis-fargate"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_ENV"),
Value: pulumi.StringPtr("e2e-test"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_VERSION"),
Value: pulumi.StringPtr("1.0"),
},
},
DockerLabels: pulumi.StringMap{
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:fargate\"]"),
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:fargate\"]"),
"com.datadoghq.tags.service": pulumi.String("redis-fargate"),
"com.datadoghq.tags.env": pulumi.String("e2e-test"),
"com.datadoghq.tags.version": pulumi.String("1.0"),
},
Cpu: pulumi.IntPtr(0),
Essential: pulumi.BoolPtr(true),
Expand Down
46 changes: 46 additions & 0 deletions test/e2e-framework/components/datadog/apps/tracegen/ecs.go
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,29 @@ func EcsAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, opts ...
Name: pulumi.StringPtr("DD_TRACE_AGENT_URL"),
Value: pulumi.StringPtr("unix:///var/run/datadog/apm.socket"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_SERVICE"),
Value: pulumi.StringPtr("tracegen-test-service"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_ENV"),
Value: pulumi.StringPtr("e2e-test"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_VERSION"),
Value: pulumi.StringPtr("1.0"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_LOGS_INJECTION"),
Value: pulumi.StringPtr("true"),
},
},
DockerLabels: pulumi.StringMap{
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:ec2\"]"),
"com.datadoghq.ad.logs": pulumi.String("[{\"source\":\"tracegen\",\"service\":\"tracegen-test-service\"}]"),
"com.datadoghq.tags.service": pulumi.String("tracegen-test-service"),
"com.datadoghq.tags.env": pulumi.String("e2e-test"),
"com.datadoghq.tags.version": pulumi.String("1.0"),
},
Cpu: pulumi.IntPtr(10),
Memory: pulumi.IntPtr(32),
Expand Down Expand Up @@ -92,6 +115,29 @@ func EcsAppDefinition(e aws.Environment, clusterArn pulumi.StringInput, opts ...
Name: pulumi.StringPtr("ECS_AGENT_HOST"),
Value: pulumi.StringPtr("true"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_SERVICE"),
Value: pulumi.StringPtr("tracegen-test-service"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_ENV"),
Value: pulumi.StringPtr("e2e-test"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_VERSION"),
Value: pulumi.StringPtr("1.0"),
},
ecs.TaskDefinitionKeyValuePairArgs{
Name: pulumi.StringPtr("DD_LOGS_INJECTION"),
Value: pulumi.StringPtr("true"),
},
},
DockerLabels: pulumi.StringMap{
"com.datadoghq.ad.tags": pulumi.String("[\"ecs_launch_type:ec2\"]"),
"com.datadoghq.ad.logs": pulumi.String("[{\"source\":\"tracegen\",\"service\":\"tracegen-test-service\"}]"),
"com.datadoghq.tags.service": pulumi.String("tracegen-test-service"),
"com.datadoghq.tags.env": pulumi.String("e2e-test"),
"com.datadoghq.tags.version": pulumi.String("1.0"),
},
Cpu: pulumi.IntPtr(10),
Memory: pulumi.IntPtr(32),
Expand Down
17 changes: 17 additions & 0 deletions test/e2e-framework/resources/aws/ecs/nodeGroups.go
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,23 @@ func NewWindowsNodeGroup(e aws.Environment, clusterName pulumi.StringInput) (pul
return newNodeGroup(e, "win2022-ng", pulumi.String(winAmi.Value), pulumi.String(e.DefaultInstanceType()), getUserData(windowsInitUserData, clusterName))
}

// NewManagedNodeGroup creates an ECS node group using ECS-managed instances.
// Managed instances are EC2 instances that are managed by ECS, providing automatic scaling,
// draining, and lifecycle management without requiring direct ASG management.
func NewManagedNodeGroup(e aws.Environment, clusterName pulumi.StringInput) (pulumi.StringOutput, error) {
// Use the same ECS-optimized AMI as regular node groups
ecsAmi, err := ssm.LookupParameter(e.Ctx(), &ssm.LookupParameterArgs{
Name: "/aws/service/ecs/optimized-ami/amazon-linux-2/recommended/image_id",
}, e.WithProvider(config.ProviderAWS))
if err != nil {
return pulumi.StringOutput{}, err
}

// Managed instances use similar configuration but with ECS-managed ASG
// For testing purposes, we create a standard node group that ECS will manage
return newNodeGroup(e, "managed-ng", pulumi.String(ecsAmi.Value), pulumi.String(e.DefaultInstanceType()), getUserData(linuxInitUserData, clusterName))
}

func newNodeGroup(e aws.Environment, ngName string, ami, instanceType, userData pulumi.StringInput) (pulumi.StringOutput, error) {
lt, err := ec2.CreateLaunchTemplate(e, ngName,
ami,
Expand Down
71 changes: 71 additions & 0 deletions test/e2e-framework/resources/aws/ecs/wait.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
// Unless explicitly stated otherwise all files in this repository are licensed
// under the Apache License Version 2.0.
// This product includes software developed at Datadog (https://www.datadoghq.com/).
// Copyright 2025-present Datadog, Inc.

package ecs

import (
"context"
"fmt"
"time"

"github.com/DataDog/datadog-agent/test/e2e-framework/resources/aws"
awssdk "github.com/aws/aws-sdk-go-v2/aws"
awsconfig "github.com/aws/aws-sdk-go-v2/config"
"github.com/aws/aws-sdk-go-v2/service/ecs"
"github.com/pulumi/pulumi/sdk/v3/go/pulumi"
)

// WaitForContainerInstances waits for at least minInstances container instances to be registered
// in the ECS cluster before returning. Returns the cluster ARN as a StringOutput so it can be
// used as an implicit dependency for downstream resources.
func WaitForContainerInstances(e aws.Environment, clusterArn pulumi.StringOutput, minInstances int) pulumi.StringOutput {
return pulumi.All(clusterArn).ApplyT(func(args []interface{}) (string, error) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

WaitForContainerInstances blocks with time.Sleep inside ApplyT; uses ambient AWS region
wait.go:399–448 - 5-min polling loop with sleep inside ApplyT goroutine. Also awsconfig.LoadDefaultConfig(ctx) ignores Pulumi stack region.

clusterArnStr := args[0].(string)

ctx := context.Background()
cfg, err := awsconfig.LoadDefaultConfig(ctx,
awsconfig.WithRegion(e.Region()),
awsconfig.WithSharedConfigProfile(e.Profile()),
)
if err != nil {
return "", fmt.Errorf("failed to load AWS config: %w", err)
}

ecsClient := ecs.NewFromConfig(cfg)

maxWaitTime := 5 * time.Minute
pollInterval := 10 * time.Second
startTime := time.Now()

e.Ctx().Log.Info(fmt.Sprintf("Waiting for at least %d container instance(s) to register in cluster %s", minInstances, clusterArnStr), nil)

for {
if time.Since(startTime) > maxWaitTime {
return "", fmt.Errorf("timeout waiting for container instances after %v", maxWaitTime)
}

listOutput, err := ecsClient.ListContainerInstances(ctx, &ecs.ListContainerInstancesInput{
Cluster: awssdk.String(clusterArnStr),
Status: "ACTIVE",
})
if err != nil {
e.Ctx().Log.Warn(fmt.Sprintf("Failed to list container instances: %v, retrying...", err), nil)
time.Sleep(pollInterval)
continue
}

registeredCount := len(listOutput.ContainerInstanceArns)
e.Ctx().Log.Info(fmt.Sprintf("Found %d registered container instance(s) (need %d)", registeredCount, minInstances), nil)

if registeredCount >= minInstances {
e.Ctx().Log.Info(fmt.Sprintf("Container instances ready! Found %d instance(s)", registeredCount), nil)
return clusterArnStr, nil
}

e.Ctx().Log.Info(fmt.Sprintf("Waiting %v before checking again...", pollInterval), nil)
time.Sleep(pollInterval)
}
}).(pulumi.StringOutput)
}
Loading
Loading