Skip to content

Commit 26f32ac

Browse files
committed
Disable internet by default on Host provisioners
This is the behavioral change: the Host provisioner now defaults to no-internet access unless the test explicitly calls ec2.WithInternetAccess(). Changes: - resources/aws/ec2/vm.go: security group selection based on WithoutInternetAccess - resources/aws/environment.go: add NoInternetSecurityGroupNames() helper - resources/aws/environmentDefaults.go: set no-internet for agentQa environment - scenarios/aws/ec2/vm.go: pass withoutInternetAccess through to InstanceArgs - testing/provisioners/aws/host/host.go: prepend WithoutInternetAccess as the provisioner default (caller-provided opts including WithInternetAccess() run after and can override it) - components/datadog/agent/host_linuxos.go: use S3 URL (no internet needed) - components/datadog/updater/install_script.sh: use S3 URL - tests/agent-platform/install/install.go: use S3/internal URL - tests/fleet/agent/install.go: use S3/internal URL - examples: add WithoutInternetAccess() to examples that need it - remote-config/tracer_test.go: switch to Provisioner (fakeintake) so the test no longer needs internet at all
1 parent 4a1fddd commit 26f32ac

12 files changed

Lines changed: 79 additions & 25 deletions

File tree

test/e2e-framework/components/datadog/agent/host_linuxos.go

Lines changed: 21 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -35,16 +35,17 @@ func (am *agentLinuxManager) getInstallCommand(version agentparams.PackageVersio
3535
testEnvVars := []string{}
3636

3737
if version.PipelineID != "" {
38-
testEnvVars = append(testEnvVars, fmt.Sprintf("TESTING_APT_URL=apttesting.datad0g.com/datadog-agent/pipeline-%v-a%v", version.PipelineID, version.Major))
38+
testEnvVars = append(testEnvVars, fmt.Sprintf("TESTING_APT_URL=s3.amazonaws.com/apttesting.datad0g.com/datadog-agent/pipeline-%v-a%v", version.PipelineID, version.Major))
3939
// apt testing repo
4040
// TESTING_APT_REPO_VERSION="pipeline-xxxxx-a7 7"
4141
testEnvVars = append(testEnvVars, fmt.Sprintf(`TESTING_APT_REPO_VERSION="stable-%[1]s %[2]v"`, am.targetOS.Descriptor().Architecture, version.Major))
42-
testEnvVars = append(testEnvVars, "TESTING_YUM_URL=yumtesting.datad0g.com")
42+
testEnvVars = append(testEnvVars, "TESTING_YUM_URL=s3.amazonaws.com/yumtesting.datad0g.com")
4343
// yum testing repo
4444
// TESTING_YUM_VERSION_PATH="testing/pipeline-xxxxx-a7/7"
4545
testEnvVars = append(testEnvVars, fmt.Sprintf("TESTING_YUM_VERSION_PATH=testing/pipeline-%[1]v-a%[2]v/%[2]v", version.PipelineID, version.Major))
4646
// target testing keys
47-
testEnvVars = append(testEnvVars, fmt.Sprintf("TESTING_KEYS_URL=apttesting.datad0g.com/test-keys"))
47+
testEnvVars = append(testEnvVars, fmt.Sprintf("TESTING_KEYS_URL=s3.amazonaws.com/apttesting.datad0g.com/test-keys"))
48+
testEnvVars = append(testEnvVars, "TESTING_REPORT_URL=undefined")
4849
} else {
4950
testEnvVars = append(testEnvVars, fmt.Sprintf("DD_AGENT_MAJOR_VERSION=%v", version.Major))
5051

@@ -53,8 +54,24 @@ func (am *agentLinuxManager) getInstallCommand(version agentparams.PackageVersio
5354
}
5455

5556
if version.Channel != "" && version.Channel != agentparams.StableChannel {
56-
testEnvVars = append(testEnvVars, "REPO_URL=datad0g.com")
57+
// Non-stable channel (e.g. beta): packages are on datad0g.com. Use S3 bucket
58+
// URLs directly instead of REPO_URL so that VMs without public internet access
59+
// can reach them via the S3 VPC gateway endpoint.
60+
testEnvVars = append(testEnvVars, "DD_REPO_URL=datad0g.com")
61+
testEnvVars = append(testEnvVars, "TESTING_REPORT_URL=undefined")
62+
testEnvVars = append(testEnvVars, "TESTING_APT_URL=s3.amazonaws.com/apt.datad0g.com")
63+
testEnvVars = append(testEnvVars, "TESTING_YUM_URL=s3.amazonaws.com/yum.datad0g.com")
64+
testEnvVars = append(testEnvVars, "TESTING_KEYS_URL=s3.amazonaws.com/public-signing-keys")
5765
testEnvVars = append(testEnvVars, fmt.Sprintf("DD_AGENT_DIST_CHANNEL=%s", version.Channel))
66+
} else {
67+
// No pipeline ID and stable channel: installing from the default datadoghq.com repos.
68+
// Use S3 bucket URLs directly instead of the CloudFront-backed domains so that
69+
// VMs without public internet access can reach them via the S3 VPC gateway endpoint.
70+
testEnvVars = append(testEnvVars, "TESTING_APT_URL=s3.amazonaws.com/apt.datadoghq.com")
71+
testEnvVars = append(testEnvVars, "TESTING_YUM_URL=s3.amazonaws.com/yum.datadoghq.com")
72+
testEnvVars = append(testEnvVars, "TESTING_KEYS_URL=s3.amazonaws.com/public-signing-keys")
73+
testEnvVars = append(testEnvVars, "TESTING_REPORT_URL=undefined")
74+
5875
}
5976
}
6077

test/e2e-framework/components/datadog/updater/install_script.sh

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,4 +20,4 @@ TESTING_APT_URL="apttesting.datad0g.com/datadog-agent/pipeline-${DD_PIPELINE_ID}
2020
TESTING_APT_REPO_VERSION="stable-$(uname -m | sed 's/aarch64/arm64/; s/amd64/x86_64/') 7" \
2121
TESTING_YUM_URL="yumtesting.datad0g.com" \
2222
TESTING_YUM_VERSION_PATH="testing/pipeline-${DD_PIPELINE_ID}-a7/7" \
23-
bash -c "$(curl -L https://install.datadoghq.com/scripts/install_script_agent7.sh)"
23+
bash -c "$(curl -L https://s3.amazonaws.com/dd-agent/scripts/install_script_agent7.sh)"

test/e2e-framework/resources/aws/ec2/vm.go

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@
66
package ec2
77

88
import (
9+
"fmt"
10+
911
"github.com/DataDog/datadog-agent/test/e2e-framework/common/config"
1012
"github.com/DataDog/datadog-agent/test/e2e-framework/common/utils"
1113
"github.com/DataDog/datadog-agent/test/e2e-framework/resources/aws"
@@ -26,10 +28,11 @@ type InstanceArgs struct {
2628
InstanceProfile string
2729

2830
// Optional
29-
UserData string
30-
HTTPTokensRequired bool
31-
HostID pulumi.StringInput // For dedicated host tenancy
32-
VolumeThroughput int // GP3 volume throughput in MiB/s (125-1000)
31+
UserData string
32+
HTTPTokensRequired bool
33+
HostID pulumi.StringInput // For dedicated host tenancy
34+
VolumeThroughput int // GP3 volume throughput in MiB/s (125-1000)
35+
WithoutInternetAccess bool // Replaces the account's default security groups with groups resolved from e.NoInternetSecurityGroupNames()
3336
}
3437

3538
func NewInstance(e aws.Environment, name string, args InstanceArgs, opts ...pulumi.ResourceOption) (*ec2.Instance, error) {
@@ -43,12 +46,31 @@ func NewInstance(e aws.Environment, name string, args InstanceArgs, opts ...pulu
4346
rootBlockDevice.VolumeType = pulumi.String("gp3")
4447
rootBlockDevice.Throughput = pulumi.Int(args.VolumeThroughput)
4548
}
49+
var securityGroups []string
50+
if args.WithoutInternetAccess {
51+
sgNames := e.NoInternetSecurityGroupNames()
52+
if len(sgNames) == 0 {
53+
return nil, fmt.Errorf("no security groups configured to block internet access, set the %s config parameter", aws.DDInfraNoInternetSecurityGroupNamesParamName)
54+
}
55+
for _, sgName := range sgNames {
56+
sg, err := ec2.LookupSecurityGroup(e.Ctx(), &ec2.LookupSecurityGroupArgs{
57+
Name: pulumi.StringRef(sgName),
58+
VpcId: pulumi.StringRef(e.DefaultVPCID()),
59+
}, e.WithProvider(config.ProviderAWS))
60+
if err != nil {
61+
return nil, fmt.Errorf("failed to lookup no-internet security group %q: %w", sgName, err)
62+
}
63+
securityGroups = append(securityGroups, sg.Id)
64+
}
65+
} else {
66+
securityGroups = e.DefaultSecurityGroups()
67+
}
4668
instanceArgs := &ec2.InstanceArgs{
4769
Ami: pulumi.StringPtr(args.AMI),
4870
SubnetId: e.RandomSubnets().Index(pulumi.Int(0)),
4971
IamInstanceProfile: pulumi.StringPtr(args.InstanceProfile),
5072
InstanceType: pulumi.StringPtr(args.InstanceType),
51-
VpcSecurityGroupIds: pulumi.ToStringArray(e.DefaultSecurityGroups()),
73+
VpcSecurityGroupIds: pulumi.ToStringArray(securityGroups),
5274
KeyName: pulumi.StringPtr(args.KeyPairName),
5375
UserData: pulumi.StringPtr(args.UserData),
5476
UserDataReplaceOnChange: pulumi.BoolPtr(true),

test/e2e-framework/resources/aws/environment.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ const (
3131
DDInfraDefaultVPCIDParamName = "aws/defaultVPCID"
3232
DDInfraDefaultSubnetsParamName = "aws/defaultSubnets"
3333
DDInfraDefaultSecurityGroupsParamName = "aws/defaultSecurityGroups"
34+
DDInfraNoInternetSecurityGroupNamesParamName = "aws/noInternetSecurityGroupNames"
3435
DDInfraDefaultInstanceTypeParamName = "aws/defaultInstanceType"
3536
DDInfraDefaultInstanceProfileParamName = "aws/defaultInstanceProfile"
3637
DDInfraDefaultARMInstanceTypeParamName = "aws/defaultARMInstanceType"
@@ -258,6 +259,14 @@ func (e *Environment) DefaultSecurityGroups() []string {
258259
return e.GetStringListWithDefault(e.InfraConfig, DDInfraDefaultSecurityGroupsParamName, e.envDefault.ddInfra.defaultSecurityGroups)
259260
}
260261

262+
// NoInternetSecurityGroupNames returns the names of security groups to attach to a VM instead of
263+
// the account's default security groups when internet access must be blocked. The groups are
264+
// resolved to IDs at provisioning time via LookupSecurityGroup; they must already exist in the
265+
// account's VPC and be configured accordingly.
266+
func (e *Environment) NoInternetSecurityGroupNames() []string {
267+
return e.GetStringListWithDefault(e.InfraConfig, DDInfraNoInternetSecurityGroupNamesParamName, e.envDefault.ddInfra.noInternetSecurityGroupNames)
268+
}
269+
261270
func (e *Environment) DefaultInstanceType() string {
262271
return e.GetStringWithDefault(e.InfraConfig, DDInfraDefaultInstanceTypeParamName, e.envDefault.ddInfra.defaultInstanceType)
263272
}

test/e2e-framework/resources/aws/environmentDefaults.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ type ddInfra struct {
4040
defaultVPCID string
4141
defaultSubnets []SubnetConfig
4242
defaultSecurityGroups []string
43+
noInternetSecurityGroupNames []string
4344
defaultInstanceType string
4445
defaultInstanceProfileName string
4546
defaultARMInstanceType string
@@ -168,6 +169,7 @@ func agentSandboxDefault() environmentDefault {
168169
{ID: "subnet-003831c49a10df3dd", MacOSCompatible: false},
169170
},
170171
defaultSecurityGroups: []string{"sg-038231b976eb13d44", "sg-05466e7ce253d21b1"},
172+
noInternetSecurityGroupNames: []string{"no-internet-access"},
171173
defaultInstanceType: "t3.medium",
172174
defaultInstanceProfileName: "ec2InstanceRole",
173175
defaultARMInstanceType: "t4g.medium",
@@ -238,6 +240,7 @@ func agentQADefault() environmentDefault {
238240
{ID: "subnet-0dabe4bab92b2b9a7", MacOSCompatible: true}, // us-east-1b
239241
},
240242
defaultSecurityGroups: []string{"sg-05e9573fcc582f22c", "sg-0498c960a173dff1e"},
243+
noInternetSecurityGroupNames: []string{"no-internet-access"},
241244
defaultInstanceType: "t3.medium",
242245
defaultInstanceProfileName: "ec2InstanceRole",
243246
defaultARMInstanceType: "t4g.medium",

test/e2e-framework/scenarios/aws/ec2/vm.go

Lines changed: 9 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -51,14 +51,15 @@ func NewVM(e aws.Environment, name string, params ...VMOption) (*remote.Host, er
5151
c.CloudProvider = pulumi.String(components.CloudProviderAWS).ToStringOutput()
5252

5353
instanceArgs := ec2.InstanceArgs{
54-
AMI: amiInfo.id,
55-
InstanceType: vmArgs.instanceType,
56-
UserData: vmArgs.userData,
57-
InstanceProfile: vmArgs.instanceProfile,
58-
HTTPTokensRequired: vmArgs.httpTokensRequired,
59-
Tenancy: vmArgs.tenancy,
60-
HostID: pulumi.String(vmArgs.hostID),
61-
VolumeThroughput: vmArgs.volumeThroughput,
54+
AMI: amiInfo.id,
55+
InstanceType: vmArgs.instanceType,
56+
UserData: vmArgs.userData,
57+
InstanceProfile: vmArgs.instanceProfile,
58+
HTTPTokensRequired: vmArgs.httpTokensRequired,
59+
Tenancy: vmArgs.tenancy,
60+
HostID: pulumi.String(vmArgs.hostID),
61+
VolumeThroughput: vmArgs.volumeThroughput,
62+
WithoutInternetAccess: vmArgs.withoutInternetAccess,
6263
}
6364

6465
if vmArgs.osInfo.Family() == os.MacOSFamily && vmArgs.hostID == "" {

test/e2e-framework/testing/provisioners/aws/host/host.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,8 @@ func Provisioner(opts ...ProvisionerOption) provisioners.TypedProvisioner[enviro
7474
provisioner := provisioners.NewTypedPulumiProvisioner(provisionerBaseID+runParams.Name, func(ctx *pulumi.Context, env *environments.Host) error {
7575
// We ALWAYS need to make a deep copy of `params`, as the provisioner can be called multiple times.
7676
// and it's easy to forget about it, leading to hard to debug issues.
77+
// Prepend the no-internet default so that caller-provided opts (e.g. ec2.WithInternetAccess()) can override it.
78+
opts = append([]ProvisionerOption{WithRunOptions(ec2.WithEC2InstanceOptions(ec2.WithoutInternetAccess()))}, opts...)
7779
params := getProvisionerParams(opts...)
7880
runParams := ec2.GetParams(params.runOptions...)
7981

test/new-e2e/examples/agentenv_logs_test.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ func TestVMLogsExampleSuite(t *testing.T) {
3232
e2e.Run(t, &vmLogsExampleSuite{}, e2e.WithProvisioner(
3333
awshost.Provisioner(
3434
awshost.WithRunOptions(
35+
ec2.WithEC2InstanceOptions(ec2.WithoutInternetAccess()),
3536
ec2.WithAgentOptions(
3637
agentparams.WithIntegration("custom_logs.d", customLogsConfig),
3738
agentparams.WithLogs(),

test/new-e2e/examples/vm_test.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ package examples
88
import (
99
"testing"
1010

11+
"github.com/DataDog/datadog-agent/test/e2e-framework/scenarios/aws/ec2"
1112
"github.com/DataDog/datadog-agent/test/e2e-framework/testing/e2e"
1213
"github.com/DataDog/datadog-agent/test/e2e-framework/testing/environments"
1314
awshost "github.com/DataDog/datadog-agent/test/e2e-framework/testing/provisioners/aws/host"
@@ -19,7 +20,7 @@ type vmSuite struct {
1920

2021
// TestVMSuite runs tests for the VM interface to ensure its implementation is correct.
2122
func TestVMSuite(t *testing.T) {
22-
suiteParams := []e2e.SuiteOption{e2e.WithProvisioner(awshost.ProvisionerNoAgentNoFakeIntake())}
23+
suiteParams := []e2e.SuiteOption{e2e.WithProvisioner(awshost.ProvisionerNoAgentNoFakeIntake(awshost.WithRunOptions(ec2.WithEC2InstanceOptions(ec2.WithoutInternetAccess()))))}
2324

2425
e2e.Run(t, &vmSuite{}, suiteParams...)
2526
}

test/new-e2e/tests/agent-platform/install/install.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ func Unix(t *testing.T, client ExecutorWithRetry, options ...installparams.Optio
6767
var source string
6868
if params.MajorVersion != "5" {
6969
source = "S3"
70-
downloadCmd = fmt.Sprintf(`curl -L https://install.datadoghq.com/scripts/install_script_agent%v.sh > installscript.sh`, params.MajorVersion)
70+
downloadCmd = fmt.Sprintf(`curl -L https://s3.amazonaws.com/dd-agent/scripts/install_script_agent%v.sh > installscript.sh`, params.MajorVersion)
7171
} else {
7272
source = "dd-agent repository"
7373
downloadCmd = "curl -L https://raw.githubusercontent.com/DataDog/dd-agent/master/packaging/datadog-agent/source/install_agent.sh > installscript.sh"
@@ -112,5 +112,4 @@ exit 1
112112
_, err := client.ExecuteWithRetry(cmd)
113113
require.NoError(tt, err, "failed to install the agent: ", err)
114114
})
115-
116115
}

0 commit comments

Comments
 (0)