Skip to content

Commit

Permalink
chore: Merge pull request #15 from ublue-os/tepene/host-config
Browse files Browse the repository at this point in the history
feat: host configuration
  • Loading branch information
tepene authored May 6, 2023
2 parents a2973d0 + 402fefe commit 12176c5
Show file tree
Hide file tree
Showing 12 changed files with 249 additions and 31 deletions.
6 changes: 6 additions & 0 deletions .vscode/cspell_custom.txt
Original file line number Diff line number Diff line change
@@ -1,9 +1,15 @@
configmap
devcontainer
devcontainers
ENDCOLOR
ensurepath
getent
gitmessage
hostvars
keygen
lineinfile
minica
Mountpoint
pipx
rvproxy
ublue
Expand Down
10 changes: 8 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,12 @@ You can use the the user `ublue` and password `ublue` to login.
> At the moment there's only a dummy project included. Tasks for real life usage
> will be included soon.
## Firing Up the Forge
## Handling the forge

To heat up the forge run `./setup.sh`.
You can use the `forge.sh` to **setup**, **heat-up** and **cool-down** the forge.

| Command | Description |
| ---------------------- | -------------------------------------------- |
| `./forge.sh setup` | Setup the forge for the first time or update |
| `./forge.sh heat-up` | Start the forge |
| `./forge.sh cool-down` | Stop the forge |
37 changes: 31 additions & 6 deletions forge-pod.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@ kind: Pod
metadata:
name: ublue-os_forge
spec:
restartPolicy: Always
restartPolicy: OnFailure
volumes:
- name: ublue-os_forge-minica-pvc
- name: ublue-os_forge-certs-pvc
persistentVolumeClaim:
claimName: ublue-os_forge-minica
claimName: ublue-os_forge-certs

- name: ublue-os_forge-registry-pvc
persistentVolumeClaim:
Expand All @@ -28,7 +28,7 @@ spec:
cpu: 200m
volumeMounts:
- mountPath: /certs
name: ublue-os_forge-minica-pvc
name: ublue-os_forge-certs-pvc
ports:
- containerPort: 443
hostPort: 443
Expand All @@ -42,7 +42,7 @@ spec:
cpu: 200m
volumeMounts:
- mountPath: /certs
name: ublue-os_forge-minica-pvc
name: ublue-os_forge-certs-pvc
subPath: _.ublue.local
- mountPath: /var/lib/registry
name: ublue-os_forge-registry-pvc
Expand All @@ -59,12 +59,37 @@ spec:
volumeMounts:
- mountPath: /var/lib/semaphore
name: ublue-os_forge-semaphore-pvc
- mountPath: /certs
subPath: ssh
name: ublue-os_forge-certs-pvc
readOnly: true
ports:
- containerPort: 3000
protocol: TCP

- name: setup.ublue.local
image: setup
volumeMounts:
- mountPath: /certs
name: ublue-os_forge-certs-pvc
readOnly: true
env:
- name: ANSIBLE_FORGE_HOST_USER
valueFrom:
secretKeyRef:
name: ublue-os_forge-secure
key: ANSIBLE_FORGE_HOST_USER

- name: ANSIBLE_FORGE_HOST_BECOME_PASSWORD
valueFrom:
secretKeyRef:
name: ublue-os_forge-secure
key: ANSIBLE_FORGE_HOST_BECOME_PASSWORD
workingDir: /ansible
command:
- ansible-playbook
args:
- main.yml
resources:
limits:
memory: 512Mi
Expand All @@ -75,4 +100,4 @@ spec:
image: minica
volumeMounts:
- mountPath: /certs
name: ublue-os_forge-minica-pvc
name: ublue-os_forge-certs-pvc
135 changes: 135 additions & 0 deletions forge.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
#!/bin/bash

# Functions
function setup {
echo -e "${YELLOW}Checking pre-requisites...${ENDCOLOR}"
check_prerequisites
echo -e "${YELLOW}Creating secret configuration...${ENDCOLOR}"
create_secrets
echo -e "${YELLOW}Heating up forge for the first time...${ENDCOLOR}"
podman play kube forge-pod.yml --build --replace & PID_BUILD=$!
wait ${PID_BUILD}
echo -e "${YELLOW}Configuring host system...${ENDCOLOR}"
configure_host & PID_CONFIG=$!
wait ${PID_CONFIG}
echo -e "${YELLOW}Configuring forge...${ENDCOLOR}"
podman logs --color -f ublue-os_forge-setup.ublue.local
echo ""
echo -e "${YELLOW}Cleaning up secrets...${ENDCOLOR}"
delete_secrets
show_info
echo -e "${GREEN}Done. Happy forging!${ENDCOLOR}"
}

function up {
echo -e "${YELLOW}Heating up forge...${ENDCOLOR}"
podman pod start ublue-os_forge
echo -e "${GREEN}Done. Happy forging!${ENDCOLOR}"
}

function down {
echo -e "${YELLOW}Cooling down forge...${ENDCOLOR}"
podman pod stop ublue-os_forge --ignore
echo -e "${GREEN}Done. Have a nice day${ENDCOLOR}"
}

function configure_host {
if [ ! -f ~/.config/.ublue-os_forge-host-setup-done ];
then
echo "adding ssh public key to ~/.ssh/authorized_keys"
VOLUME_DIR="$(podman volume inspect ublue-os_forge-certs | jq -r '.[0].Mountpoint')"
SSH_PUBLIC_KEY_FILE="${VOLUME_DIR}/ssh/ublue-os_forge-id_ed25519.pub"
SSH_PUBLIC_KEY="$(cat ${SSH_PUBLIC_KEY_FILE})"
echo "#uBlue forge ssh key" >> ~/.ssh/authorized_keys
echo "$SSH_PUBLIC_KEY" >> ~/.ssh/authorized_keys
cp -f ${VOLUME_DIR}/tls/ublue-os_forge-root.pem ~/Downloads
touch ~/.config/.ublue-os_forge-host-setup-done
echo ""
else
echo "Host system already configured. Nothing to do..."
echo ""
fi
}

function create_secrets {
# Get user input
echo -e "${YELLOW}Gathering user input${ENDCOLOR}"
read -s -p "Enter sudo password for user $USER: " ANSIBLE_FORGE_HOST_BECOME_PASSWORD
cat <<EOF | jq '.|map_values(@base64)' | podman secret create ublue-os_forge-secure - >/dev/null
{
"ANSIBLE_FORGE_HOST_USER": "$USER",
"ANSIBLE_FORGE_HOST_BECOME_PASSWORD": "${ANSIBLE_FORGE_HOST_BECOME_PASSWORD}"
}
EOF
echo ""
}

function delete_secrets {
podman secret rm ublue-os_forge-secure
}

function check_prerequisites {
echo -e "${YELLOW}Checking sshd service${ENDCOLOR}"
SSH_SERVICE_STATUS="$(systemctl is-active sshd)"
if [ "${SSH_SERVICE_STATUS}" = "inactive" ];
then
echo -e "${RED}It looks like your sshd service is not running.${ENDCOLOR}"
echo -e "${RED}Make sure to configure and start it first.${ENDCOLOR}"
exit 1
else
echo -e "${GREEN}sshd service is ${SSH_SERVICE_STATUS}${ENDCOLOR}"
echo ""
fi
echo -e "${YELLOW}Checking podman installation${ENDCOLOR}"
PODMAN_PATH=$(which podman 2>/dev/null || echo 'FALSE')
if [ "$PODMAN_PATH" == "FALSE" ];
then
echo -e "${RED}It looks like podman is not installed.${ENDCOLOR}"
echo -e "${RED}Make sure to install it first.${ENDCOLOR}"
exit 1
else
echo -e "${GREEN}podman is installed${SSH_SERVICE_STATUS}${ENDCOLOR}"
echo ""
fi
echo -e "${YELLOW}Checking jq installation${ENDCOLOR}"
JQ_PATH=$(which jq 2>/dev/null || echo 'FALSE')
if [ "$JQ_PATH" == "FALSE" ];
then
echo -e "${RED}It looks like jq is not installed.${ENDCOLOR}"
echo -e "${RED}Make sure to install it first.${ENDCOLOR}"
exit 1
else
echo -e "${GREEN}jq is installed${SSH_SERVICE_STATUS}${ENDCOLOR}"
echo ""
fi
}

function show_info {
VOLUME_DIR="$(podman volume inspect ublue-os_forge-certs | jq -r '.[0].Mountpoint')"
echo -e "${GREEN}uBlue forge is available at: https://forge.ublue.local${ENDCOLOR}"
echo -e "${GREEN}To trust the certificate in your Browser of choice, make sure to import the root certificate from:${ENDCOLOR}"
echo -e "${GREEN}$HOME/Downloads/tls/ublue-os_forge-root.pem${ENDCOLOR}"
echo ""
}

# Bash colors
RED="\e[31m"
YELLOW="\e[33m"
GREEN="\e[32m"
ENDCOLOR="\e[0m"

# Main
case "$1" in
setup)
setup
;;
heat-up)
up
;;
cool-down)
down
;;
*)
echo "Invalid argument: please provide 'heat-up', 'cool-down', or 'setup'"
;;
esac
11 changes: 7 additions & 4 deletions minica/Containerfile
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
# Source Image
FROM docker.io/library/golang:1.20

# Copy script
WORKDIR /certs
COPY certificates.sh .
RUN chmod +x ./certificates.sh

# Install minica
RUN go install github.com/jsha/minica@latest

# Generate wildcard certificate
WORKDIR /certs
RUN minica --domains "*.ublue.local,ublue.local,localhost" \
--ip-addresses 127.0.0.1
# Container start command
CMD ["/certs/certificates.sh"]
27 changes: 27 additions & 0 deletions minica/certificates.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
#!/bin/sh
## Create SSH keys and certificates for uBlue-OS Forge

CERTIFICATE_DIRECTORY="/certs"
SSH_KEY_NAME="ublue-os_forge-id_ed25519"
TLS_ROOT_CERTIFICATE_NAME="ublue-os_forge-root"

if [ ! -f ${CERTIFICATE_DIRECTORY}/ssh/${SSH_KEY_NAME} ];
then
echo "uBlue Forge SSH key not present. Creating new key..."
mkdir ${CERTIFICATE_DIRECTORY}/ssh -p
# Generate SSH key
ssh-keygen -o -a 100 -t ed25519 -f ${CERTIFICATE_DIRECTORY}/ssh/${SSH_KEY_NAME} -C "[email protected]"
else
echo "Existing uBlue Forge SSH key found. Nothing to do..."
fi

# Creating TLS certificates
if [ ! -f ${CERTIFICATE_DIRECTORY}/tls/${TLS_ROOT_CERTIFICATE_NAME}.pem ];
then
echo "uBlue Forge TLS root not certificate present. Creating new certificates..."
mkdir ${CERTIFICATE_DIRECTORY}/tls -p
# Generate TLS certificates
minica --domains "*.ublue.local,ublue.local,localhost" --ip-addresses 127.0.0.1 -ca-cert "${CERTIFICATE_DIRECTORY}/tls/${TLS_ROOT_CERTIFICATE_NAME}.pem" -ca-key "${CERTIFICATE_DIRECTORY}/tls/${TLS_ROOT_CERTIFICATE_NAME}-key.pem"
else
echo "Existing uBlue Forge TLS root certificate found. Nothing to do..."
fi
2 changes: 1 addition & 1 deletion rvproxy/Caddyfile
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
reverse_proxy ublue-os_forge-registry.ublue.local:5000 {
transport http {
tls
tls_trusted_ca_certs /certs/minica.pem
tls_trusted_ca_certs /certs/tls/ublue-os_forge-root.pem
}
}
}
Expand Down
4 changes: 0 additions & 4 deletions setup.sh

This file was deleted.

11 changes: 5 additions & 6 deletions setup/Containerfile
Original file line number Diff line number Diff line change
@@ -1,11 +1,10 @@
# Source Image
FROM docker.io/library/python:alpine3.17

# Install forge setup project
COPY ./ansible /ansible
RUN pip3 install -r /ansible/requirements.txt
RUN chmod +x /ansible/startup.sh
# Install SSH
RUN apk add openssh

# Run starup script
# Install ansible and dependencies
WORKDIR /ansible
CMD ["./startup.sh"]
COPY ./ansible .
RUN pip3 install -r ./requirements.txt
2 changes: 2 additions & 0 deletions setup/ansible/ansible.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ roles_path = ./roles
collections_paths = ./collections
# Localtion for plugins & modules
library = ./library
# SSH
private_key_file = /certs/ssh/ublue-os_forge-id_ed25519
# Console log settings
display_skipped_hosts = false
# Use the stdout_callback when running ad-hoc commands.
Expand Down
28 changes: 27 additions & 1 deletion setup/ansible/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@
groups:
- forge
ansible_host: "{{ container_host_ip }}"
ansible_user: "{{ lookup('ansible.builtin.env', 'ANSIBLE_FORGE_HOST_USER') }}"
ansible_become_password: "{{ lookup('ansible.builtin.env', 'ANSIBLE_FORGE_HOST_BECOME_PASSWORD') }}"

- name: Add Ansible Semaphore to inventory
ansible.builtin.add_host:
Expand All @@ -30,7 +32,31 @@
ansible_connection: local
ansible_python_interpreter: "{{ ansible_playbook_python }}"

## TODO: Add play to configure host system
- name: Configure host system
hosts: forge
gather_facts: true
tasks:
- name: Add ublue.local entries to /etc/hosts
ansible.builtin.lineinfile:
path: /etc/hosts
search_string: 127.0.0.1 registry.ublue.local forge.ublue.local
line: 127.0.0.1 registry.ublue.local forge.ublue.local
state: present
become: true

- name: Add ublue.local TSL root certificate to trust anchors
ansible.builtin.copy:
src: /certs/tls/ublue-os_forge-root.pem
dest: /etc/pki/ca-trust/source/anchors/ublue-os_forge-root.pem
force: true
mode: "0644"
become: true

- name: Update ca-trust store
ansible.builtin.command:
cmd: update-ca-trust
changed_when: false
become: true

- name: Configure Ansible Semaphore
hosts: semaphore
Expand Down
7 changes: 0 additions & 7 deletions setup/ansible/startup.sh

This file was deleted.

0 comments on commit 12176c5

Please sign in to comment.