<p>As a part of a bigger module, I want to deploy an <code>nginx</code> container and replace its default <code>nginx.conf</code>. The new config should be built using Terraform <em>resources</em>' data which is generated at the time of deployment. Is there a way to do it?</p>

<p>I managed to replace the standard nginx.conf with a dynamically generated one following these steps:</p>
<ol>
<li>Create a template config file with placeholders for dynamic data</li>
<li>Parse the file using Terraform's <code>template_file</code> <em>data source</em></li>
<li>Store the parsed data in a ConfigMap and mount the map as a volume for the Nginx container</li>
</ol>
<p>Step by step:</p>
<p>Create nginx.conf template named <strong>nginx-conf.tpl</strong>:</p>
<pre><code>events {
  worker_connections  4096;  ## Default: 1024
}
http {
  server {
    listen 80;
    listen [::]:80;

    server_name ${server_name};

    location /_plugin/kibana {
        proxy_pass https://${elasticsearch_kibana_endpoint};
    }
    location / {
        proxy_pass https://${elasticsearch_endpoint};
    }
  }
}
</code></pre>
<p>Parse the <strong>nginx-conf.tpl</strong> template with the following Terraform code:</p>
<pre><code>data &quot;template_file&quot; &quot;nginx&quot; {
  template = &quot;${file(&quot;${path.module}/nginx-conf.tpl&quot;)}&quot;
  vars = {
    elasticsearch_endpoint        = &quot;${aws_elasticsearch_domain.example-name.endpoint}&quot;
    elasticsearch_kibana_endpoint = &quot;${aws_elasticsearch_domain.example-name.kibana_endpoint}&quot;
    server_name                   = &quot;${var.server_name}&quot;
  }
}
</code></pre>
<p>Create a ConfigMap and store the parsed template there with <code>nginx.conf</code> key:</p>
<pre><code>resource &quot;kubernetes_config_map&quot; &quot;nginx&quot; {
  metadata {
    name = &quot;nginx&quot;
  }
  data = {
    &quot;nginx.conf&quot; = data.template_file.nginx.rendered
  }
}
</code></pre>
<p>Finally, mount the ConfigMap key as a container volume:</p>
<pre><code># ...
spec {
  # ...
  container {
    # ...
    volume_mount {
      name       = &quot;nginx-conf&quot;
      mount_path = &quot;/etc/nginx&quot;
    }
  }
  volume {
    name = &quot;nginx-conf&quot;
    config_map {
      name = &quot;nginx&quot;
      items {
        key  = &quot;nginx.conf&quot;
        path = &quot;nginx.conf&quot;
      }
    }
  }
}
# ...
</code></pre>
<p>That's it. Nginx server will start using the provided config.</p>
<p>Useful links: <a href="https://kubernetes.io/docs/concepts/storage/volumes/#configmap" rel="nofollow noreferrer">Kubernetes ConfigMap as volume</a>, <a href="https://registry.terraform.io/providers/hashicorp/template/latest/docs/data-sources/file" rel="nofollow noreferrer">Terraform temple_file data source doc</a>.</p>
