DevOps: Dealing with local secrets, environment variables and GPG

in #devops3 years ago

This article shows how we make use of environment variables and GPG to easily switch between credentials for various deployments. In our particular case, we have various Hashicorp clusters (nomad, consul, vault, ...) deployed and need to be able to switch between them conveniently and securely.

In particular, this articles aims for improved usability of local secrets in contrast to Identity and Access Management (IAM).

Security

Obviously, access credentials to your cloud orchestration has to be kept
confidential. As such, we store our credentials encrypted using gpg/gpg.

Environment Variables

At least on Linux, dealing with credentials is most convenient going through
environment variables which are read my most of the tools anyhow.

Example

As an example, here is the content of a GPG encrypted file for one of our
environments:

TARGET=[staging|prod|infra]
NOMAD_ADDR=https://nomad.staging.example.com
NOMAD_TOKEN=**************************
VAULT_ADDR=https://vault.staging.example.com
VAULT_TOKEN=**************************
CONSUL_HTTP_ADDR=https://consul.staging.example.com
CONSUL_HTTP_AUTH=**************************
MC_HOST_infra=https://username:**************************@minio.staging.example.com
TF_VAR_hcloud_token=**************************

As you can see, we use a variable TARGET to identify which environment we are
working with (dev, staging, prod, infra).

The content of the file is encrypted using:

gpg -sear Fabian -o
~/Documents/Encrypted/Environments/staging.example.com.gpg

At this place, let me recommend the vim-plugin jamessan/vim-gnupg which takes
care of editing the file afterwards.

Loading Function

For easy loading of your encrypted environment variables, I wrote a shell (zsh)
script:

def loadenv() {
  export $(gpg -d ~/Documents/Encrypted/Environments/$1.gpg | xargs -0)
}

Usage

In case i need to load environment, all I need to do is:

loadenv staging.example.com

and i get all the variables loaded and ready to go.

Bonus Material

Since we make heavy use of make, here are a few snippets that are useful in
your Makefile:

ifndef NOMAD_TOKEN
$(error NOMAD_TOKEN required!)
endif

ifndef VAULT_TOKEN
$(error VAULT_TOKEN required!)
endif

ifndef TARGET
$(error TARGET ['staging','prod', 'infra'] required!)
endif
.PHONY: tunnel
tunnel:
ifeq ($(TARGET), infra)
        ssh -N -f -L 4646:10.0.4.2:4646 root@machine1
        ssh -N -f -L 8200:10.0.4.2:8200 root@machine1
        ssh -N -f -L 8500:localhost:8500 root@machine1
endif
ifeq ($(TARGET), staging)
        ssh -N -f -L 4646:10.1.0.4:4646 root@machine2
        ssh -N -f -L 8200:10.1.0.2:8200 root@machine2
        ssh -N -f -L 8500:localhost:8500 root@machine2
endif

And for terraform:

set_consul: clean
    CONSUL_ADDRESS="$(CONSUL_ADDRESS)" envsubst < terraform.tf.template > terraform.tf

set_workspace:
    terraform workspace select $(TARGET)

init: set_consul
    terraform init -var-file $(TARGET).tfvars
    ([[ -z "`terraform workspace list | grep $(TARGET)`" ]] && terraform workspace new $(TARGET)) || exit 0

plan: set_workspace
    terraform plan -var-file $(TARGET).tfvars

apply: set_workspace
    terraform apply -var-file $(TARGET).tfvars
Sort:  

Congratulations @chainsquad! You received a personal badge!

Happy Hive Birthday! You are on the Hive blockchain for 5 years!

You can view your badges on your board and compare yourself to others in the Ranking

Check out the last post from @hivebuzz:

Hive Power Up Month - Quick feedback
Feedback from the September 1st Hive Power Up Day
Introducing the Hive Power Up Month - Let's grow every day!