fix: add direct to project (#118)

* fix: cross link direct access
---------

Signed-off-by: matttrach <matt.trachier@suse.com>
This commit is contained in:
Matt Trachier 2025-05-05 10:22:06 -05:00 committed by matttrach
parent ddafbe9db1
commit bd65ca94f1
No known key found for this signature in database
GPG Key ID: E082F2592F87D4AE
8 changed files with 154 additions and 48 deletions

47
.envrc
View File

@ -1,26 +1,48 @@
#!/bin/env sh #!/bin/env sh
nf () {
nix --extra-experimental-features nix-command --extra-experimental-features flakes "$@"
}
get_repo_basename() {
basename "$(git rev-parse --show-toplevel)"
}
get_profile() {
basename="$(get_repo_basename)"
echo "$HOME/.config/nix/profiles/$basename"
}
cleanup() { cleanup() {
echo "Cleaning Up..." echo "Cleaning Up..."
basename="$(get_repo_basename)"
echo 'Getting Nix Usage...' profile="$(get_profile)"
echo "Nix store is using $(du -hs /nix/store)" if [ -z "$basename" ]; then echo "basename is empty"; exit 1; fi
export NIX_PATH="$profile"
echo 'Archiving Nix Profile...' export NIX_PROFILE="$profile"
nix develop --profile /tmp/terraform-aws-server-nix-env --extra-experimental-features nix-command --extra-experimental-features flakes --command bash -c "echo done" nix-env --profile "$profile" --delete-generations +3
nix-env --profile "$profile" --list-generations
} }
if ! which "$0" | grep -q nix; then if ! which "$0" | grep -q nix; then
print 'Entering Environment...' print 'Entering Environment...'
basename="$(get_repo_basename)"
profile="$(get_profile)"
export NIX_PROFILE="$profile"
print 'Updating Nix Cache...' print 'Updating Nix Cache...'
nix flake update --extra-experimental-features nix-command --extra-experimental-features flakes nf flake update
echo 'Installing Nix Profile...'
nf profile install . --profile "$profile"
nf profile list --profile "$profile"
print 'Starting...' print 'Starting...'
nix develop \ # --impure allows Nix to reuse previously built paths
# --ignore-environment ignores the environment variables and paths to tools not installed by nix
nf develop \
--ignore-environment \ --ignore-environment \
--extra-experimental-features nix-command \ --impure \
--extra-experimental-features flakes \
--keep HOME \ --keep HOME \
--keep SSH_AUTH_SOCK \ --keep SSH_AUTH_SOCK \
--keep GITHUB_TOKEN \ --keep GITHUB_TOKEN \
@ -30,9 +52,12 @@ if ! which "$0" | grep -q nix; then
--keep AWS_ACCESS_KEY_ID \ --keep AWS_ACCESS_KEY_ID \
--keep AWS_SECRET_ACCESS_KEY \ --keep AWS_SECRET_ACCESS_KEY \
--keep AWS_SESSION_TOKEN \ --keep AWS_SESSION_TOKEN \
--keep KUBE_CONFIG_PATH \
--keep TERM \ --keep TERM \
--keep XDG_DATA_DIRS \ --keep XDG_DATA_DIRS \
/tmp/terraform-aws-server-nix-env \ --keep NIX_SSL_CERT_FILE \
--keep NIX_PROFILE \
--profile "$profile" \
--command bash -c "bash --rcfile .envrc" --command bash -c "bash --rcfile .envrc"
print 'Exiting Dev Environment...' print 'Exiting Dev Environment...'

1
.gitignore vendored
View File

@ -19,3 +19,4 @@ examples/*/50-*
*.lock *.lock
*.DS_* *.DS_*
test/data/* test/data/*
*.test

View File

@ -5,11 +5,11 @@
"systems": "systems" "systems": "systems"
}, },
"locked": { "locked": {
"lastModified": 1710146030, "lastModified": 1731533236,
"narHash": "sha256-SZ5L6eA7HJ/nmkzGG7/ISclqe6oZdOZTNoesiInkXPQ=", "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=",
"owner": "numtide", "owner": "numtide",
"repo": "flake-utils", "repo": "flake-utils",
"rev": "b1d9ab70662946ef0850d488da1c9019f3a9752a", "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b",
"type": "github" "type": "github"
}, },
"original": { "original": {
@ -20,11 +20,11 @@
}, },
"nixpkgs": { "nixpkgs": {
"locked": { "locked": {
"lastModified": 1724395761, "lastModified": 1746152631,
"narHash": "sha256-zRkDV/nbrnp3Y8oCADf5ETl1sDrdmAW6/bBVJ8EbIdQ=", "narHash": "sha256-zBuvmL6+CUsk2J8GINpyy8Hs1Zp4PP6iBWSmZ4SCQ/s=",
"owner": "NixOS", "owner": "NixOS",
"repo": "nixpkgs", "repo": "nixpkgs",
"rev": "ae815cee91b417be55d43781eb4b73ae1ecc396c", "rev": "032bc6539bd5f14e9d0c51bd79cfe9a055b094c3",
"type": "github" "type": "github"
}, },
"original": { "original": {

View File

@ -58,6 +58,7 @@
gitleaks gitleaks
gnupg gnupg
go go
golint
gotestfmt gotestfmt
gotestsum gotestsum
jq jq
@ -72,6 +73,7 @@
updatecli updatecli
vim vim
which which
yq-go
]; ];
}; };

View File

@ -173,4 +173,5 @@ module "direct_access" {
type = "A" # we will enable ipv6 in the future type = "A" # we will enable ipv6 in the future
ips = distinct([module.server[0].public_ip, module.server[0].private_ip]) ips = distinct([module.server[0].public_ip, module.server[0].private_ip])
} }
server_security_group_name = local.server_security_group_name
} }

View File

@ -13,6 +13,32 @@ locals {
# tflint-ignore: terraform_unused_declarations # tflint-ignore: terraform_unused_declarations
fail_domain_ips = ((local.add_domain && length(local.domain_ips) == 0) ? one([local.domain_ips, "missing_domain_ips"]) : false) fail_domain_ips = ((local.add_domain && length(local.domain_ips) == 0) ? one([local.domain_ips, "missing_domain_ips"]) : false)
all_ips = compact(concat(local.domain_ips, [(local.add_eip ? aws_eip.created[0].public_ip : "")])) all_ips = compact(concat(local.domain_ips, [(local.add_eip ? aws_eip.created[0].public_ip : "")]))
server_security_group_name = var.server_security_group_name
access_address_cidrs_length = [
for i in range(length(local.access_addresses)) :
length(local.access_addresses[keys(local.access_addresses)[i]].cidrs)
] # [1,1,2,2,1]
access_address_cidrs_matrix = merge([
for ia in range(length(local.access_addresses)) :
{
for ib in range(local.access_address_cidrs_length[ia]) :
"${keys(local.access_addresses)[ia]}-${ib}" => {
port = local.access_addresses[keys(local.access_addresses)[ia]].port
cidr = local.access_addresses[keys(local.access_addresses)[ia]].cidrs[ib]
ip_family = local.access_addresses[keys(local.access_addresses)[ia]].ip_family
protocol = local.access_addresses[keys(local.access_addresses)[ia]].protocol
}
}
]...)
}
data "aws_security_group" "server_security_group" {
filter {
name = "tag:Name"
values = [local.server_security_group_name]
}
} }
resource "aws_security_group" "direct_access" { resource "aws_security_group" "direct_access" {
@ -24,18 +50,28 @@ resource "aws_security_group" "direct_access" {
} }
} }
resource "aws_security_group_rule" "server_ingress" { resource "aws_vpc_security_group_ingress_rule" "server_ingress" {
depends_on = [ depends_on = [
aws_security_group.direct_access, aws_security_group.direct_access,
] ]
for_each = local.access_addresses for_each = local.access_address_cidrs_matrix
security_group_id = aws_security_group.direct_access.id security_group_id = aws_security_group.direct_access.id
type = "ingress"
from_port = each.value.port from_port = each.value.port
to_port = each.value.port to_port = each.value.port
protocol = each.value.protocol ip_protocol = each.value.protocol
cidr_blocks = (each.value.ip_family != "ipv6" ? each.value.cidrs : null) cidr_ipv4 = (each.value.ip_family != "ipv6" ? each.value.cidr : null)
ipv6_cidr_blocks = (each.value.ip_family == "ipv6" ? each.value.cidrs : null) cidr_ipv6 = (each.value.ip_family == "ipv6" ? each.value.cidr : null)
}
# allow the server's security group direct access to the server
resource "aws_vpc_security_group_ingress_rule" "server_direct_link" {
depends_on = [
aws_security_group.direct_access,
data.aws_security_group.server_security_group,
]
security_group_id = aws_security_group.direct_access.id
referenced_security_group_id = data.aws_security_group.server_security_group.id
ip_protocol = -1
} }
resource "aws_network_interface_sg_attachment" "server_security_group_attachment" { resource "aws_network_interface_sg_attachment" "server_security_group_attachment" {
@ -46,7 +82,6 @@ resource "aws_network_interface_sg_attachment" "server_security_group_attachment
network_interface_id = local.server.network_interface_id network_interface_id = local.server.network_interface_id
} }
resource "aws_eip" "created" { resource "aws_eip" "created" {
count = local.add_eip ? 1 : 0 count = local.add_eip ? 1 : 0
domain = "vpc" domain = "vpc"
@ -87,7 +122,8 @@ resource "terraform_data" "setup" {
aws_eip.created, aws_eip.created,
aws_eip_association.created, aws_eip_association.created,
aws_network_interface_sg_attachment.server_security_group_attachment, aws_network_interface_sg_attachment.server_security_group_attachment,
aws_security_group_rule.server_ingress, aws_vpc_security_group_ingress_rule.server_ingress,
aws_vpc_security_group_ingress_rule.server_direct_link,
aws_security_group.direct_access, aws_security_group.direct_access,
] ]
count = (local.use_strategy == "ssh" ? 1 : 0) count = (local.use_strategy == "ssh" ? 1 : 0)
@ -125,7 +161,8 @@ resource "terraform_data" "remove_initial_user" {
terraform_data.setup, terraform_data.setup,
aws_eip_association.created, aws_eip_association.created,
aws_network_interface_sg_attachment.server_security_group_attachment, aws_network_interface_sg_attachment.server_security_group_attachment,
aws_security_group_rule.server_ingress, aws_vpc_security_group_ingress_rule.server_ingress,
aws_vpc_security_group_ingress_rule.server_direct_link,
aws_security_group.direct_access, aws_security_group.direct_access,
] ]
count = (local.use_strategy == "ssh" ? 1 : 0) count = (local.use_strategy == "ssh" ? 1 : 0)

View File

@ -127,3 +127,11 @@ variable "add_eip" {
If set to true, we will add an elastic ip to the instance. If set to true, we will add an elastic ip to the instance.
EOT EOT
} }
variable "server_security_group_name" {
type = string
description = <<-EOT
The name for the security group that the server is on.
We will allow direct access to this security group as well as the cidrs in the access address objects.
EOT
}

View File

@ -3,16 +3,30 @@
rerun_failed=false rerun_failed=false
specific_test="" specific_test=""
specific_package="" specific_package=""
cleanup_id=""
while getopts ":r:t:p:" opt; do while getopts ":r:t:p:c:" opt; do
case $opt in case $opt in
r) rerun_failed=true ;; r) rerun_failed=true ;;
t) specific_test="$OPTARG" ;; t) specific_test="$OPTARG" ;;
p) specific_package="$OPTARG" ;; p) specific_package="$OPTARG" ;;
\?) echo "Invalid option -$OPTARG" >&2 && exit 1 ;; c) cleanup_id="$OPTARG" ;;
\?) cat <<EOT >&2 && exit 1 ;;
Invalid option -$OPTARG, valid options are
-r to re-run failed tests
-t to specify a specific test (eg. TestBase)
-p to specify a specific test package (eg. base)
-c to run clean up only with the given id (eg. abc123)
EOT
esac esac
done done
if [ -n "$cleanup_id" ]; then
export IDENTIFIER="$cleanup_id"
fi
REPO_ROOT="$(git rev-parse --show-toplevel)"
run_tests() { run_tests() {
local rerun=$1 local rerun=$1
REPO_ROOT="$(git rev-parse --show-toplevel)" REPO_ROOT="$(git rev-parse --show-toplevel)"
@ -94,13 +108,31 @@ if [ -z "$GITHUB_TOKEN" ]; then echo "GITHUB_TOKEN isn't set"; else echo "GITHUB
if [ -z "$GITHUB_OWNER" ]; then echo "GITHUB_OWNER isn't set"; else echo "GITHUB_OWNER is set"; fi if [ -z "$GITHUB_OWNER" ]; then echo "GITHUB_OWNER isn't set"; else echo "GITHUB_OWNER is set"; fi
if [ -z "$ZONE" ]; then echo "ZONE isn't set"; else echo "ZONE is set"; fi if [ -z "$ZONE" ]; then echo "ZONE isn't set"; else echo "ZONE is set"; fi
# Run tests initially if [ -z "$cleanup_id" ]; then
run_tests false echo "checking tests for compile errors..."
D="$(pwd)"
cd "$REPO_ROOT/test/tests" || exit
if ! go mod tidy; then echo "failed to tidy, exit code $?"; exit 1; fi
# Check if we need to rerun failed tests while IFS= read -r file; do
if [ "$rerun_failed" = true ] && [ -f "/tmp/${IDENTIFIER}_failed_tests.txt" ]; then echo "found $file";
if ! go test -c "$file"; then C=$?; echo "failed to compile $file, exit code $C"; exit $C; fi
done < "$(find "$REPO_ROOT/test" -name '*.go')"
echo "compile checks passed..."
cd "$D" || exit
echo "checking terraform configs for errors..."
if ! tflint --recursive; then C=$?; echo "tflint failed, exit code $C"; exit $C; fi
echo "terraform configs valid..."
# Run tests initially
run_tests false
# Check if we need to rerun failed tests
if [ "$rerun_failed" = true ] && [ -f "/tmp/${IDENTIFIER}_failed_tests.txt" ]; then
echo "Rerunning failed tests..." echo "Rerunning failed tests..."
run_tests true run_tests true
fi
fi fi
echo "Clearing leftovers with Id $IDENTIFIER in $AWS_REGION..." echo "Clearing leftovers with Id $IDENTIFIER in $AWS_REGION..."
@ -121,8 +153,8 @@ if [ -n "$IDENTIFIER" ]; then
attempts=0 attempts=0
# shellcheck disable=SC2143 # shellcheck disable=SC2143
while [ -n "$(leftovers -d --iaas=aws --aws-region="$AWS_REGION" --type="ec2-key-pair" --filter="tf-$IDENTIFIER" | grep -v 'AccessDenied')" ] && [ $attempts -lt 3 ]; do while [ -n "$(leftovers -d --iaas=aws --aws-region="$AWS_REGION" --type="ec2-key-pair" --filter="terraform-ci-$IDENTIFIER" | grep -v 'AccessDenied')" ] && [ $attempts -lt 3 ]; do
leftovers --iaas=aws --aws-region="$AWS_REGION" --type="ec2-key-pair" --filter="tf-$IDENTIFIER" --no-confirm | grep -v 'AccessDenied' || true leftovers --iaas=aws --aws-region="$AWS_REGION" --type="ec2-key-pair" --filter="terraform-ci-$IDENTIFIER" --no-confirm | grep -v 'AccessDenied' || true
sleep 10 sleep 10
attempts=$((attempts + 1)) attempts=$((attempts + 1))
done done