ansible: Deploy ARA
[ARA Records Ansible][0] is a results storage system for Ansible. It provides a convenient UI for tracking Ansible playbooks and tasks. The data are populated by an Ansible callback plugin. ARA is a fairly simple Python+Django application. It needs a database to store Ansible results, so we've connected it to the main PostgreSQL database and configured it to connect and authenticate using mTLS. Rather than mess with managing and distributing a static password for ARA clients, I've configured Autheliad to allow anonymous access to post data to the ARA API from within the private network or the Kubernetes cluster. Access to the web UI does require authentication. [0]: https://ara.recordsansible.org/
This commit is contained in:
1
ansible/.gitignore
vendored
Normal file
1
ansible/.gitignore
vendored
Normal file
@@ -0,0 +1 @@
|
||||
ara/.secrets.toml
|
||||
87
ansible/ara.yaml
Normal file
87
ansible/ara.yaml
Normal file
@@ -0,0 +1,87 @@
|
||||
apiVersion: v1
|
||||
kind: Service
|
||||
metadata:
|
||||
name: ara
|
||||
labels: &labels
|
||||
app.kubernetes.io/name: ara
|
||||
app.kubernetes.io/component: ara
|
||||
spec:
|
||||
selector: *labels
|
||||
type: ClusterIP
|
||||
ports:
|
||||
- name: http
|
||||
port: 8000
|
||||
targetPort: 8000
|
||||
|
||||
---
|
||||
apiVersion: apps/v1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: ara
|
||||
labels: &labels
|
||||
app.kubernetes.io/name: ara
|
||||
app.kubernetes.io/component: ara
|
||||
spec:
|
||||
selector:
|
||||
matchLabels: *labels
|
||||
template:
|
||||
metadata:
|
||||
labels: *labels
|
||||
spec:
|
||||
enableServiceLinks: false
|
||||
containers:
|
||||
- name: ara-api
|
||||
image: quay.io/recordsansible/ara-api
|
||||
env:
|
||||
- name: ARA_BASE_DIR
|
||||
value: /etc/ara
|
||||
- name: ARA_SETTINGS
|
||||
value: /etc/ara/settings.toml
|
||||
- name: SECRETS_FOR_DYNACONF
|
||||
value: /etc/ara/.secrets.toml
|
||||
ports:
|
||||
- containerPort: 8000
|
||||
name: http
|
||||
readinessProbe: &probe
|
||||
httpGet:
|
||||
port: 8000
|
||||
path: /api/
|
||||
httpHeaders:
|
||||
- name: Host
|
||||
value: ara.ansible.pyrocufflink.blue
|
||||
failureThreshold: 3
|
||||
periodSeconds: 60
|
||||
successThreshold: 1
|
||||
timeoutSeconds: 5
|
||||
startupProbe:
|
||||
<<: *probe
|
||||
failureThreshold: 30
|
||||
initialDelaySeconds: 1
|
||||
periodSeconds: 1
|
||||
timeoutSeconds: 1
|
||||
volumeMounts:
|
||||
- mountPath: /etc/ara/settings.toml
|
||||
name: config
|
||||
subPath: settings.toml
|
||||
readOnly: true
|
||||
- mountPath: /etc/ara/.secrets.toml
|
||||
name: secrets
|
||||
subPath: .secrets.toml
|
||||
readOnly: true
|
||||
- mountPath: /tmp
|
||||
name: tmp
|
||||
subPath: tmp
|
||||
securityContext:
|
||||
runAsNonRoot: true
|
||||
runAsUser: 7653
|
||||
runAsGroup: 7653
|
||||
volumes:
|
||||
- name: config
|
||||
configMap:
|
||||
name: ara
|
||||
- name: secrets
|
||||
secret:
|
||||
secretName: ara
|
||||
- name: tmp
|
||||
emptyDir:
|
||||
medium: Memory
|
||||
38
ansible/ara/settings.toml
Normal file
38
ansible/ara/settings.toml
Normal file
@@ -0,0 +1,38 @@
|
||||
[default]
|
||||
ALLOWED_HOSTS = [
|
||||
'ara.ansible.pyrocufflink.blue',
|
||||
]
|
||||
LOG_LEVEL = 'INFO'
|
||||
TIME_ZONE = 'UTC'
|
||||
|
||||
EXTERNAL_AUTH = true
|
||||
READ_LOGIN_REQUIRED = false
|
||||
WRITE_LOGIN_REQUIRED = false
|
||||
|
||||
DATABASE_ENGINE = 'django.db.backends.postgresql'
|
||||
DATABASE_HOST = 'postgresql.pyrocufflink.blue'
|
||||
DATABASE_NAME = 'ara'
|
||||
DATABASE_USER = 'ara'
|
||||
|
||||
[default.DATABASE_OPTIONS]
|
||||
sslmode = 'verify-full'
|
||||
sslcert = '/run/secrets/ara/postgresql/tls.crt'
|
||||
sslkey = '/run/secrets/ara/postgresql/tls.key'
|
||||
sslrootcert = '/run/dch-ca/dch-root-ca.crt'
|
||||
|
||||
[default.LOGGING]
|
||||
version = 1
|
||||
disable_existing_loggers = false
|
||||
|
||||
[default.LOGGING.formatters.normal]
|
||||
format = '%(levelname)s %(name)s: %(message)s'
|
||||
|
||||
[default.LOGGING.handlers.console]
|
||||
class = 'logging.StreamHandler'
|
||||
formatter = 'normal'
|
||||
level = 'INFO'
|
||||
|
||||
[default.LOGGING.loggers.ara]
|
||||
handlers = ['console']
|
||||
level = 'INFO'
|
||||
propagate = false
|
||||
32
ansible/ingress.yaml
Normal file
32
ansible/ingress.yaml
Normal file
@@ -0,0 +1,32 @@
|
||||
apiVersion: networking.k8s.io/v1
|
||||
kind: Ingress
|
||||
metadata:
|
||||
name: ara
|
||||
labels:
|
||||
app.kubernetes.io/name: ara
|
||||
app.kubernetes.io/component: ara
|
||||
annotations:
|
||||
cert-manager.io/cluster-issuer: dch-ca
|
||||
nginx.ingress.kubernetes.io/proxy-buffer-size: "8k"
|
||||
nginx.ingress.kubernetes.io/auth-method: GET
|
||||
nginx.ingress.kubernetes.io/auth-url: http://authelia.authelia.svc.cluster.local:9091/api/verify
|
||||
nginx.ingress.kubernetes.io/auth-signin: https://auth.pyrocufflink.blue/?rm=$request_method
|
||||
nginx.ingress.kubernetes.io/auth-snippet: |
|
||||
proxy_set_header X-Forwarded-Method $request_method;
|
||||
spec:
|
||||
ingressClassName: nginx
|
||||
tls:
|
||||
- hosts:
|
||||
- ara.ansible.pyrocufflink.blue
|
||||
secretName: ara-cert
|
||||
rules:
|
||||
- host: ara.ansible.pyrocufflink.blue
|
||||
http:
|
||||
paths:
|
||||
- path: /
|
||||
pathType: Prefix
|
||||
backend:
|
||||
service:
|
||||
name: ara
|
||||
port:
|
||||
name: http
|
||||
58
ansible/kustomization.yaml
Normal file
58
ansible/kustomization.yaml
Normal file
@@ -0,0 +1,58 @@
|
||||
apiVersion: kustomize.config.k8s.io/v1beta1
|
||||
kind: Kustomization
|
||||
|
||||
labels:
|
||||
- pairs:
|
||||
app.kubernetes.io/instance: ansible
|
||||
includeSelectors: true
|
||||
includeTemplates: true
|
||||
- pairs:
|
||||
app.kubernetes.io/part-of: ansible
|
||||
|
||||
namespace: ansible
|
||||
|
||||
resources:
|
||||
- ../dch-root-ca
|
||||
- secrets.yaml
|
||||
- namespace.yaml
|
||||
- ara.yaml
|
||||
- postgres-cert.yaml
|
||||
- ingress.yaml
|
||||
|
||||
configMapGenerator:
|
||||
- name: ara
|
||||
files:
|
||||
- ara/settings.toml
|
||||
options:
|
||||
labels:
|
||||
app.kubernetes.io/name: ara
|
||||
|
||||
patches:
|
||||
- patch: |-
|
||||
apiVersion: apps/v1
|
||||
kind: Deployment
|
||||
metadata:
|
||||
name: ara
|
||||
spec:
|
||||
template:
|
||||
spec:
|
||||
containers:
|
||||
- name: ara-api
|
||||
volumeMounts:
|
||||
- mountPath: /run/dch-ca/dch-root-ca.crt
|
||||
name: dch-root-ca
|
||||
subPath: dch-root-ca.crt
|
||||
readOnly: true
|
||||
- mountPath: /run/secrets/ara/postgresql
|
||||
name: postgresql-cert
|
||||
readOnly: true
|
||||
securityContext:
|
||||
fsGroup: 7653
|
||||
volumes:
|
||||
- name: postgresql-cert
|
||||
secret:
|
||||
secretName: ara-postgres-cert
|
||||
defaultMode: 0640
|
||||
- name: dch-root-ca
|
||||
configMap:
|
||||
name: dch-root-ca
|
||||
6
ansible/namespace.yaml
Normal file
6
ansible/namespace.yaml
Normal file
@@ -0,0 +1,6 @@
|
||||
apiVersion: v1
|
||||
kind: Namespace
|
||||
metadata:
|
||||
name: ansible
|
||||
labels:
|
||||
app.kubernetes.io/name: ansible
|
||||
12
ansible/postgres-cert.yaml
Normal file
12
ansible/postgres-cert.yaml
Normal file
@@ -0,0 +1,12 @@
|
||||
apiVersion: cert-manager.io/v1
|
||||
kind: Certificate
|
||||
metadata:
|
||||
name: ara-postgres-cert
|
||||
spec:
|
||||
commonName: ara
|
||||
privateKey:
|
||||
algorithm: ECDSA
|
||||
secretName: ara-postgres-cert
|
||||
issuerRef:
|
||||
name: postgresql-ca
|
||||
kind: ClusterIssuer
|
||||
19
ansible/secrets.yaml
Normal file
19
ansible/secrets.yaml
Normal file
@@ -0,0 +1,19 @@
|
||||
---
|
||||
apiVersion: bitnami.com/v1alpha1
|
||||
kind: SealedSecret
|
||||
metadata:
|
||||
name: ara
|
||||
namespace: ansible
|
||||
labels:
|
||||
app.kubernetes.io/name: ara
|
||||
app.kubernetes.io/component: ara
|
||||
spec:
|
||||
encryptedData:
|
||||
.secrets.toml: AgAiObM2t8Cmr87pMRhZN4RBqb4soEdG0OJeAmaUCl//in2LihZyOHKu5RDeLBaPneoX5G/t5eQX7KkPCW7hffjBSngVbPMZ+U8Txb1IY3uFFHGAPnJBXwHo6FgRq5uKt3LQ6UmtWLoIF4ZB4K0f/g5BHR3N6FIah/x5pKrnU9lOltVgDFSEd7Ewgrj8AorASdE7ZxBAGuUPNktQZZ9MS0d2YiOhgfZiGHDnLZoqk0osDOZzKJX47yiYg5SR4NHoGzd7gfSvBtbrU4SIQCUGZJYtOKeUGaNtCgKnLe3oCphqV3izUY1JudVF8eN5MDgUH5vG2GcqDqMYTX2oRuk+rgRjiMJTkxQ/OZlbrXGxUocTR51EoM01vgjvvCsqaE3R5MhcKE7oOHrqTXzhDY6UzBPUu6QWrkWWMegBeIVCWA2ID3m8CPljyA0oZuClqVZpx/23cs3aHcyl2vye5ey3ca5QzLkkmKK7826H3przUYdwti9gMNp0sPszsDOTzfmN9iZD33a+WvEPfbf7+ZBXBAnoH06pLXeCGc43Q2S619xdHRw4caVGeczZAWYVjlnq8BUQGmHU2Ra5W6dzYM+i3vUimJRiuzeaG+APgY4KIdZNEjPguiwg93g9NtDWgap1h5rF3Yx4nEQelEN0pNAqT8CP67gW1Kp+wjNRNHkz45Ld3mJbMsvFqjZG5cCqk1s67mBNxhani0HBJM3vEV36wnDBzWwSmemuMUdjrG0zFwQHHeZwQe7oR+9XNz1DLPxvvp6KfEbHA3YMagQa2RYxN/C9APBBC+dmk6+TJn1n
|
||||
template:
|
||||
metadata:
|
||||
name: ara
|
||||
namespace: ansible
|
||||
labels:
|
||||
app.kubernetes.io/name: ara
|
||||
app.kubernetes.io/component: ara
|
||||
@@ -5,6 +5,9 @@ access_control:
|
||||
networks:
|
||||
- 172.30.0.0/26
|
||||
- 172.31.1.0/24
|
||||
- name: cluster
|
||||
networks:
|
||||
- 10.149.0.0/16
|
||||
rules:
|
||||
- domain: paperless.pyrocufflink.blue
|
||||
policy: two_factor
|
||||
@@ -54,6 +57,16 @@ access_control:
|
||||
resources:
|
||||
- '^/submit/.*'
|
||||
policy: bypass
|
||||
- domain: ara.ansible.pyrocufflink.blue
|
||||
networks:
|
||||
- internal
|
||||
- cluster
|
||||
resources:
|
||||
- '^/api/.*'
|
||||
methods:
|
||||
- POST
|
||||
- PATCH
|
||||
policy: bypass
|
||||
|
||||
authentication_backend:
|
||||
ldap:
|
||||
|
||||
Reference in New Issue
Block a user