Extending securedrop.club

After getting started, you may want to add some host/service in securedrop.club infrastructure.

Overview

The securedrop.club infrastructure is developed and deployed using ansible. The main playbook is securedrop-club-playbook.yml.

The development, tuning and corrections of the playbook is done in a separate environment with automated testing. Molecule is the test infrastructure.

Each major playbook is related to a molecule scenario, i.e. a set of hosts and a test playbook to get a minimal infrastructure setup allowing to validate the service playbook. As an example, the weblate scenarios found in molecule/weblate/ define 4 hosts:

  • a postfix master
  • a bind server
  • a monitoring server
  • the weblate host

With these four hosts, the weblate scenario is able to test the weblate deployment, its monitoring deployment, its ability to send emails, etc.

Some very horizontal playbooks are regrouped in the misc scenario.

The presence of a bind-host in most scenarios allows to spoof all records from securedrop.club domain from an hermetic internal view (and could spoof any other domain). By the way, this disallow external requests like e.g. ACME challenge for TLS Certificates. To overcome this limitation, the domain of the scenario is defined in a one-time testing subdomain when a bind-host is used by the scenario and the variable with_fake_LE has been defined (meaning that we should use the “fake Let’s Encrypt unlimited testing infrastructure”).

At the end of integration, the preprod scenario allows to deploy all securedrop.club playbooks, in a testing subdomain.

Adding a host

Ansible hosts are defined in inventory/01-hosts.yml. This file is autogenerated by molecule scenarios. Rather than adding a host you should add a scenario.

Adding a scenario

Copying files

First we create directories:

mkdir -p molecule/dummy/roles molecule/dummy/tests

Then we select a scenario to get inspiration from. The misc scenario is a good starting point.

cp -P molecule/misc/{create,destroy,molecule}.yml molecule/dummy/

Notice the -P option for preserving links. The files create.yml and destroy.yml are linked to the infrastructure scenario.

Scenario definition

Next, edit molecule/dummy/molecule.yml. You should at least:

  • edit the scenario’s name

    scenario:
      name: dummy
    
  • define the included hosts.

    - name: dummy-host
      flavor: "s1-2"
    - name: external-host
      flavor: "s1-2"
    

The flavor refers to OVH OpenStack provisionned ressources.

At this point you should be able to:

  • create instances

    molecule create -s dummy
    
  • log into instances

    molecule login -s dummy --host dummy
    molecule login -s dummy --host external
    
  • destroy instances

    molecule destroy -s dummy
    

About hostnames

We do not use groups and each hostname matches the service it provides: securedrop.club infrastructure use service-host as naming convention. Each given host (e.g. postfix-host) is attached to a given service` (e.g. “infrastructure’s mail relay”).

So:

  • if you need to choose a hostname, derive it from the service,
  • by adding an already defined host, you will be able to deploy its (already defined) services.

Adding playbooks

The molecule default playbook is molecule/dummy/playbook.yml. It should include all playbooks used for the scenario, i.e.:

  • others scenarios playbooks, like molecule/icinga/icinga-playbook.yml or molecule/postfix/postfix-playbook.yml
  • the target scenario playbook, here molecule/icinga/dummy-playbook.yml, which is intended to be included in securedrop-club-playbook.yml. This playbook may possibly include children playbooks.
  • possibly tests specific playbooks, prepended by test, like molecule/icinga/test-dummy-playbook.yml.

Once the playbooks is added, you should be able to check its syntax and run it on a created infrastructure, via

molecule syntax -s dummy
molecule converge -s dummy

Adding tests

The purpose of the tests is mainly to detect that even if there was no error, ansible has really deployed a functional service. See them as functionnal and non-regression testing to maintaining our ansible base.

We use testinfra for this purpose. The easiest way to get started with it is to look at some existing tests. For simple testing see molecule/bind/tests/test_external_bind.py. For a request based test, see e.g. molecule/weblate/tests/test_icingaweb.py.

Since the tests run in a dedicated scenario with separated resources, you can do whatever you want (i.e. even some destructive action).

Once it has been defined, you should be able to launch it with

molecule verify -s dummy

Testing is not monitoring. You are kindly invited to setup monitoring for your services and to test via testinfra than monitoring has been setup as you wish.

Finally, you can launch a destroy, create, converge, verify, destroy cycle by launching

molecule test -s dummy

Interaction with others scenarios

Most services rely on DNS, emails and monitoring. To enable them you have to add the corresponding hosts in your molecule scenario and to include their playbook in your scenario playbook.

You will also be interested by:

  • molecule/misc/sexy-debian-playbook.yml for getting usefull tools,
  • molecule/certs/certs-playbook.yml for getting usefull TLS certificates,
  • molecule/authorized_keys/authorized-keys-playbook.yml for installing usefull keys,
  • molecule/misc/commit_etc-playbook.yml for committing /etc/ at the end of your playbook.

Documentation

You are kindly invited to document your scenario in docs. Most playbooks are documented in a dedicated file included from docs/index.rst.

Tweaking hosts

You can set ssh port, choose OS image and set default user by tweaking inventory/01-hosts.yml.