Security review
What the stack deploys, what its roles may do, what connects out and where, and what Tracemill learns.
This page is for a security or vendor review of a self-hosted deployment. It describes what the CloudFormation template creates and what the software in it does. The template is the authority: you can read it in full before launching, and every resource it creates is listed on the stack's Resources tab.
What's deployed
All in your account and the Region you choose (us-east-1 or us-west-2):
| Area | Resources |
|---|---|
| Compute | One ECS cluster (Fargate) with the Tracemill server service (1 to 4 tasks, x86_64). A second task definition runs one-off database transitions during release changes. ECS Exec is disabled. |
| Ingress | An Application Load Balancer (internet-facing or internal), HTTPS on 443 with your ACM certificate and the ELBSecurityPolicy-TLS13-1-2-2021-06 TLS policy, port 80 redirecting to 443. Optional AWS WAF web ACL. Optional alias record in a Route 53 private hosted zone. |
| Database | RDS for PostgreSQL 17. A database the stack creates is encrypted with a stack-created KMS key, not publicly accessible, has deletion protection on, requires TLS (rds.force_ssl), and exports its PostgreSQL log to CloudWatch. An existing database you supply keeps its own configuration; the stack sets none of these on it, and connects to it with TLS required by the server. |
| Identity | A Cognito user pool that only federates to your SAML or OIDC provider: no passwords, no self sign-up, no Cognito-sent email, admin-only account recovery. An emergency-access IAM role with no permissions. |
| Secrets | Secrets Manager secrets for the database master user and three application roles, the session key and the data-encryption key. |
| Storage | An S3 workspace bucket: public access blocked, SSE-S3 encryption, TLS-only bucket policy, objects expire after 14 days. |
| Logs | CloudWatch log groups for the server (30 days), transitions and stack functions (90 days each). |
| Stack machinery | Lambda functions (not in your VPC) for the release transition, its Step Functions waiter, the failure handler, snapshot housekeeping, the stack-policy guard and, if enabled, auto-apply. EventBridge rules that trigger them. An SNS topic for stack notices. |
| Network (optional) | A VPC with two public and two private subnets across two AZs, an internet gateway, one NAT gateway and an S3 gateway endpoint. |
The template has no CloudFormation transform and no nested stacks. The stack sets a stack policy on itself after every create and update that denies replacing or deleting the database it created.
IAM roles
Every role is named after the stack. Each policy is scoped to the stack's own resources except where noted.
| Role | Assumed by | May |
|---|---|---|
<stack>-task-exec | ECS, to start tasks | Pull the release's image from its ECR repository; write to the server and transition log groups; read the stack's secrets (and decrypt with your KMS key, through Secrets Manager only, if you supplied one for an existing database's secret). |
<stack>-server-task | The server | Read and write the workspace bucket; assume IAM roles for delivery (see below); read its own stack's description; write the run-activity parameter and read the rollback parameter in SSM; use five AWS License Manager actions for Marketplace licensing (Resource: *; permitted, not called by this release). |
<stack>-transition-task | Transition tasks | Read the three application-role secrets; write the release ledger mirror in SSM. The task also receives the database master credentials, which it needs to migrate. |
<stack>-stack-lambda | Stack Lambda functions | Scale and describe the Tracemill service; list, describe and stop its tasks; run the transition task definition; pass the two task roles to ECS; create, tag and delete this stack's tracemill-<id>-* database snapshots; read and write its SSM state; publish to its SNS topic; describe its stack; start its state machine. |
<stack>-auto-apply | The auto-apply function (only when enabled) | Assume the role you supply in AutoApplyRoleArn; read its SSM state; publish notices; list the service's tasks. It has no CloudFormation rights of its own. |
<stack>-waiter | Step Functions | Invoke the transition step function. |
<stack>-stack-guard | The stack-guard function | Set this stack's stack policy. |
<stack>-emergency-access | People, for emergency access | Nothing. It only identifies you to Tracemill. Not created in supplied mode. |
The one broad grant. The server task role may call sts:AssumeRole on any
role. Delivery to an S3 pipeline assumes a role you name, in any account, and
that role's trust policy is the guard: Tracemill sends the target's id as the
external id, and the role should require it. In practice, any role whose
trust policy allows your account (for example, trusts the account root
without conditions) can be assumed by the server. The server task role is
explicitly denied the auto-apply role, which can update the stack.
Updates run under the credentials of whoever updates the stack. No role is attached to the stack as its CloudFormation service role. Auto-apply updates the stack only through a role you create.
Network
- The load balancer's security group allows 443 and 80 from
AllowedIngressCidr(default0.0.0.0/0). UseAlbScheme=internalto keep the console off the internet. - Server tasks run in private subnets without public IPs and accept traffic only from the load balancer, on port 8080.
- A database the stack creates accepts traffic only from the server's security group, on 5432. An existing database keeps its own security-group rules; the stack needs one more, allowing the server's security group on 5432.
- With
EnableWaf(default on), the web ACL blocks an IP that sends more than 100 requests to/auth/paths, or more than 2,000 requests in total, within five minutes. - Outbound traffic from the tasks goes through the NAT gateway (or your own egress in an existing VPC). S3 traffic uses the gateway endpoint in a created VPC. There are no interface endpoints, so AWS API calls leave through NAT.
What connects out
To Tracemill
| Destination | From | When | What's sent |
|---|---|---|---|
Content feed, <ContentFeedBaseUrl>/rings/<Ring>/ (default https://dl.tracemill.io) | Server | Every five minutes; the content package only when a new release appears | HTTPS GET with user agent tracemill-server. No account, deployment or user identifiers. |
Release manifest, <ContentFeedBaseUrl>/rings/<Ring>/image.json | Server; auto-apply function | Server: at start, every six hours, and on Check now. Auto-apply: at each window | HTTPS GET with user agent tracemill-server or tracemill-byoc-stack. No identifiers. |
Release template, tracemill-releases-prod-us-east-1 (Amazon S3) | CloudFormation; auto-apply function | At launch and each release update; auto-apply before it applies a release | An S3 GET. |
Lambda package, tracemill-releases-prod-<Region> (Amazon S3) | AWS Lambda | At launch and each release update | An S3 GET. |
| Server image, the AWS Marketplace ECR repository | Amazon ECS | Each time a task starts | An image pull, authorised by your Marketplace subscription. |
| Sentry | Server; transition tasks | Only with SentryReporting=enabled (off by default) | Crash and error reports and warning-level log records: error type, message and stack trace. User, request, host name, breadcrumbs and device context are removed, and tags pass through an allowlist. Messages can contain internal ids such as tenant, run and target ids. |
The feed is served through a CDN, which sees each request's source address and user agent.
DeploymentReport records your consent to a future deployment report. This
release sends no report, whichever value you choose.
To AWS services in your account and Region
Cognito (sign-in and token keys), STS, SSM Parameter Store, CloudFormation (describing its own stack), S3, ECR and CloudWatch Logs from the tasks; RDS, ECS, SSM, SNS, Step Functions and CloudFormation from the stack functions. Secrets reach the tasks through ECS, not through calls from the server.
For emergency sign-in, the server forwards the proof you paste to AWS STS
(https://sts.<Region>.amazonaws.com/) to learn who signed it.
To destinations you configure
- Delivery pipelines send generated telemetry where you point them: a Splunk HTTP Event Collector endpoint, or an S3 bucket through an assumed role.
- A CrowdStrike Falcon target makes the server poll the Falcon API
(
*.crowdstrike.comor*.crowdstrike.mil) every minute with the API client credentials you provide. - Notification webhooks go to Slack (
hooks.slack.com) or Microsoft Teams (Power Platform) URLs you add. Alerts and digests carry target and detection names and posture.
What doesn't connect out
- Splunk. The TA-Tracemill add-on in your Splunk calls the console hostname with a validator key; the server never calls Splunk.
- Email. The server sends none. Stack notices to
AlertEmailare sent by Amazon SNS. Invitations aren't emailed. - No analytics, usage telemetry, billing or AI provider calls.
What stays in your account
Run results, generated telemetry, the detections you exercise, user identities, audit records and database contents never leave your account, except:
- telemetry you send yourself through a delivery pipeline;
- alert and digest content (target and detection names, posture) sent to the Slack or Teams webhooks you add;
- what an enabled Sentry report carries.
What Tracemill learns about your deployment
- From AWS Marketplace, as with any listing: your subscription and its state.
- From the feed: that a request was made, with the source address and user agent the CDN sees.
- From Sentry, only if you enable it: the reports described above.
With Sentry off, Tracemill can't tell from its own systems whether your stack is running or which release it runs.