Deploy identical Development and Production environments using Terraform

How we organised a complex multi-environment system, utilising Zero-Trust access solutions and adding support for sub-projects.
Deploy identical Development and Production environments using Terraform
SurpassSurpass
Company name:
Surpass
Industry:
Transportation Startup
R&D size:
Scale:
 Buldings Icon

1. Initial state

Surpass is a strategic projects company that built a public-transportation planning system. They created a web app to allow Public Transportation Designers to create and test how new transportation lines would behave, work, and impact current traffic and usage.

Their state when they met us:

  • Basic app, running locally on the developers' computers.
  • No ability to work with the users.
  • No environments set, or a possibility to collaborate live with other developers.
  • No deployment pipelines or version management.
Target Icon

3. Project goals

  1. Fully managed IaC-based infrastructure & environments.
  2. Developers' freedom, accessibility, and ease of use.
Checklist Icon

4. Decisions

  • Use Terraform/Terragrunt to manage the infrastructure:
    This is the most flexible IaC approach, enabling full control and integration with AWS resources.
  • Create Dev/Staging/Production environments entirely in code.
  • Develop a deployment process to deploy changes initially to Dev and later to Staging & Prod, with the appropriate tests and branching strategies in Git.
  • Lock Icon

    5. Restrictions

    We accounted for the following security-related restrictions:

    • Geo-based access restriction.
    • Usage of WAF & CloudFront.
    • A solid access control system for the internal (Private VPC) system.
    Map Icon

    6. Strategy

    The goals, decisions, and restrictions led to the following strategy:

    1. Use Terragrunt to re-use Terraform code, ensuring better observability of environments and resources. This approach allowed us to change only configuration values between environments, avoiding changes to actual code logic.
    2. Manage all secrets in AWS Secrets Manager, accessing values from GitHub Action Pipelines with multiple values set per environment.
    3. Deploy the Dev stack first, then build Staging and Production environments to improve stability, applying the same strategy for later additions.
    4. Create sub-projects following the same method.
    5. Define the correct CI/CD pipelines and branch protections for an optimal review and deployment flow.
    Settings Icon

    7. The process

    The process of creating Surpass' infrastructure was methodical and detailed:

    1. Create the Terraform module, deploy it using Terragrunt, and check for usability.
    2. Request feedback from the Dev team or the customer and make adjustments.
    3. Manage and organize the code and Infrastructure modules.

    This iterative methodology allowed us to:

    • Be agile.
    • Re-use code.
    • Adhere to customer and developer requirements.
    • Deliver value quickly, in small and manageable parts, while keeping everything tidy and neat.
    Chart Icon

    8. Results

  • The entire infrastructure is managed using Terraform.
  • Identical Dev/Staging/Production environments were created, with differences limited to each module's inputs (mostly the same).
  • Migration between AWS accounts (due to various reasons) was 10x faster compared to non-Terraform setups.
  • Each change, addition, and modification of the environment was recorded and managed in the Git repository containing Terraform/Terragrunt code.
  • The codebase remained clean and organized.
  • System services were completely isolated and inaccessible to the public web.
  • Table Icon

    9. Before & After

    Before ❌

    After ✅

    Highlight Example

    Explore how we can achieve something similar with you