Skip to main content
This document outlines how Tensor9 BYOC manages sensitive data (secrets) within your Infrastructure as Code (IaC) to ensure security and support various ownership models for the services your product relies on.

Secret ownership models

Tensor9 BYOC distinguishes between two core models for managing secrets, based on who owns the external service or resource: Vendors and customers must agree on the ownership of all external services and their associated secrets. Vendor Recommendation: While Tensor9 BYOC supports customer-supplied secrets at the infrastructure (Terraform) level, we strongly encourage migrating to a runtime secret model where the vendor’s application exposes an admin setting page for the customer to provide optional secrets after initial setup. This avoids requiring a new deployment for every secret change and makes secrets easier to manage as optional.

Terraform secret patterns

Tensor9 BYOC supports the following common industry patterns for integrating secrets into your Terraform configuration: This is the most common and recommended pattern for external services. Secrets are stored in an external secret store and retrieved during Terraform execution using a data block.

Important constraints:

  • Do not use ARNs: Tensor9 BYOC does not support referencing secrets by Amazon Resource Name (ARN). Use name-based identifiers instead, as ARNs are absolute and may not be accessible from the customer side of the appliance.
  • Use a literal secret name: Name the secret by the plain path it lives at in your own account (e.g., prod/sentry/token). Don’t build the name from a variable. Tensor9 BYOC reads the name at compile time to identify the secret, and gives each install its own isolated copy on the appliance side, so you don’t parameterize the path yourself.

2. Variable injection

Secrets are passed into the Terraform configuration as variables, typically injected via a CI/CD pipeline or .tfvars file. Important Constraint: Tensor9 BYOC requires that injected variables contain the actual secret value, not a reference (like a Secrets Manager secret ID). If you need to pass a reference, use the Runtime Fetching (Data Source) pattern instead.

3. Platform/infrastructure generated passwords (no Tensor9 support needed)

This pattern is for secrets that are automatically generated and managed by the cloud provider or Terraform itself (e.g., a database master password created by AWS RDS). Since the secret is fully encapsulated within the IaC, no special Tensor9 BYOC annotation or transfer logic is required.

Secret annotation and configuration

For the Runtime Fetching and Variable Injection patterns, you must explicitly tell Tensor9 BYOC which variables and data sources represent secrets and who owns them using a configuration file (via the tuning document or a separate JSON file). Without this annotation, Tensor9 BYOC defaults all secret-holding data sources/variables to be Vendor-owned (Shared).

Secret lifecycle and rotation

Before deployment, Tensor9 BYOC performs a pre-flight check to validate that all configured secrets meet the requirements.

Secret rotation

The process for rotating secrets depends on how the secret is referenced in your Terraform:
  1. If passing by Value: If the secret value is directly embedded in a resource definition (e.g., password = var.db_password), an update to the secret will be detected by Terraform, and a normal build and apply (deployment) will update the resource.
  2. If passing by Reference: If the infrastructure retrieves the secret by reference (e.g., a data source fetching from Secrets Manager), the infrastructure itself will not detect a change to the secret value.
    • Vendor Action Required: The vendor must trigger a refresh or a new deployment.
    • Application Logic Required: The application consuming the secret must have refresh logic built-in to periodically check for updated values.
For secrets managed via AWS Secrets Manager, Tensor9 BYOC supports the use of rotation Lambda functions. The vendor’s controller will copy the rotation Lambda function to the appliance side. This Lambda must use the ARN passed into it at runtime and must not rely on hardcoded ARNs or other references that point to the vendor’s original stack resources, since those will not resolve in the appliance.

Secrets by origin stack type

The approach to managing secrets varies by origin stack type. All approaches share the same principle: store secrets in AWS Secrets Manager or SSM Parameter Store, then pass them to your application as environment variables.

Terraform origin stacks

Define secrets in AWS Secrets Manager or SSM Parameter Store, then inject them into your compute resources as environment variables. Defining the secret:
Injecting into ECS Fargate:
Injecting into Lambda:
See Terraform Origin Stacks for complete documentation.

CloudFormation origin stacks

Use CloudFormation dynamic references to fetch secrets from Secrets Manager during stack deployment, then pass them to your resources.
See CloudFormation Origin Stacks for complete documentation.

Docker Compose origin stacks

Define secrets in the tuning document, then reference them as environment variables in your compose file. docker-compose.yml:
tuning.json:
Create release with tuning document:
See Docker Compose Origin Stacks for complete documentation.

Docker Container origin stacks

Similar to Docker Compose, define secrets in the tuning document: tuning.json:
The secrets are automatically injected as environment variables into your container. See Docker Container Origin Stacks for complete documentation.

Kubernetes origin stacks

Define secrets in AWS Secrets Manager within your Terraform/CloudFormation wrapper, then reference them in Kubernetes Deployment environment variables:
Avoid using Kubernetes Secrets directly for sensitive data. Use AWS Secrets Manager and inject values as environment variables. See Kubernetes Origin Stacks for complete documentation.

Application code (all origin stack types)

Regardless of origin stack type, your application code reads secrets from environment variables:
Environment variables provide secret values when the application starts. Applications that need to fetch a value while running can keep using AWS Secrets Manager SDK calls such as get_secret_value(). For cross-cloud deployments, the Secrets Manager service adapter serves supported calls through the configured adapter endpoint. Review its target-specific limits and configure the application’s access before deployment.