# Help Dynamically Generating CSP Nginx Include

**URL:** https://discourse.roots.io/t/help-dynamically-generating-csp-nginx-include/8967
**Category:** trellis
**Created:** 2017-03-02T17:03:11Z
**Posts:** 4

## Post 1 by @CorbinHesse — 2017-03-02T17:03:11Z

I am trying to insert Ansible variables into an nginx-include file. Unfortunately, I do not know enough about Ansible’s tasks YML format to accomplish this.

The goal is to insert the domain name from the `{{ wordpress_sites }}` dictionary into a CSP file so I can test Content Security Policies from development to production without hard-coding the domain name.

### Directory

My `nginx-includes` direction looks like this:

```
├── nginx-includes
    └── example.com
        └── csp.conf.j2
```

### `csp.conf.j2`

```
add_header Content-Security-Policy "default-src 'none'; script-src https://{{ item }};
```

### What I’ve Tried

I have tried the following only to receive errors on `vagrant reload --provision`

1. Adding `with_dict: "{{ wordpress_sites }}"` to every `name` in `roles/wordpress-setup/tasks/nginx-includes.yml`
2. Adding `{{ wordpress_sites }}` inside the `with_items:` line

The farthest I get is if I just add `{{ item }}` in `csp.conf.js` to output the following which is just the nginx path:

```
add_header Content-Security-Policy "default-src 'none'; script-src https://nginx-includes/example.com/csp.conf.j2
```

### self

I know I can use `self` in CSP, but if I can add variables from this dictionary then I could add other variables that would be needed.

Any help would be greatly appreciated. Thank you.

---

## Post 2 by @fullyint — 2017-03-02T17:50:42Z

Thanks for posting what you’ve tried.

You discovered that `{{ item }}` returns `nginx-includes/example.com/csp.conf.j2`. This is because the template task creating that file is using [`with_items`](https://github.com/roots/trellis/blob/8a6789a113f8296956164b65c80e0fe3bcfb97f2/roles/wordpress-setup/tasks/nginx-includes.yml#L32) (a [standard loop](http://docs.ansible.com/ansible/playbooks_loops.html#standard-loops)), where each `item` is a template file name.

If you switch your strategy from [include-files](https://roots.io/trellis/docs/nginx-includes/#include-files) to [child-templates](https://roots.io/trellis/docs/nginx-includes/#child-templates), the template task creating your child template will use [`with_dict`](https://github.com/roots/trellis/blob/8a6789a113f8296956164b65c80e0fe3bcfb97f2/roles/wordpress-setup/tasks/nginx.yml#L30) (thus [looping over hashes](http://docs.ansible.com/ansible/playbooks_loops.html#looping-over-hashes)), where each `item.value.somevar` is the value of `somevar` in a site from `wordpress_sites`. See example usages of `item.value` in the [`wordpress-site.conf.j2`](https://github.com/roots/trellis/blob/8a6789a113f8296956164b65c80e0fe3bcfb97f2/roles/wordpress-setup/templates/wordpress-site.conf.j2) template.

Follow the [docs for creating a child template](https://roots.io/trellis/docs/nginx-includes/#child-templates), maybe something like this (untested):

```
{% extends 'roles/nginx/templates/nginx.conf.j2' %}

  {% block server_basic -%}
  {{ super() }}
  add_header Content-Security-Policy "default-src 'none'; script-src https://{{ site_hosts_canonical | join(' https://') }};
  {% endblock %}
```

(see jinja2 [join filter](http://jinja.pocoo.org/docs/2.9/templates/#join))

You’ll see how [`site_hosts_canonical`](https://github.com/roots/trellis/blob/8a6789a113f8296956164b65c80e0fe3bcfb97f2/group_vars/all/helpers.yml#L13) is just a helper variable that itself uses `item.value.site_hosts` and the jinja2 [map filter](http://jinja.pocoo.org/docs/latest/templates/#map).

* * *

P.S., If your Trellis is up-to-date, you can apply the nginx changes more quickly than  
`vagrant reload --provision` because reloading (rebooting) the VM is not necessary, nor is most of the `provision` process. Try this:

```
ANSIBLE_TAGS=nginx-includes vagrant provision
```

---

## Post 3 by @CorbinHesse — 2017-03-10T05:03:58Z

Thank you very much for the response.

I apologize for the delay as it took me awhile to figure how to use the [child-template](https://roots.io/trellis/docs/nginx-includes/#child-templates).

Since there is a lot of customization for each site host I ended up creating a lot of these files if there were multiple hosts per Trellis installation. Therefore, I ended up creating a simple feature request on GitHub.

Also, this tip was golden!

```
ANSIBLE_TAGS=nginx-includes vagrant provision
```

Is there anyway to skip the checking/downloading of `vender/roles` during that command?

```
▶ ANSIBLE_TAGS=nginx-includes vagrant provision
==> default: Running provisioner: ansible...
    default: Running ansible-galaxy...
- downloading role 'composer', owned by geerlingguy
- downloading role from https://github.com/geerlingguy/ansible-role-composer/archive/1.5.0.tar.gz
...
```

Thanks again for your help.

---

## Post 4 by @swalkinshaw — 2017-03-10T18:48:41Z

That’s an annoying feature of Vagrant right now which is being fixed I think.

Anyway, you can use `SKIP_GALAXY=true ANSIBLE_TAGS=nginx-includes vagrant provision`
