Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(db): add entrypoint script to init database #130

Merged
merged 2 commits into from
Nov 20, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
75 changes: 75 additions & 0 deletions app/smoketest/compose/db.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
version: "3"

services:
db:
image: docker.io/library/postgres:16-bullseye
networks:
- backend
- db-admin
hostname: db
expose:
- 5432
ports:
- "5432:5432"
environment:
POSTGRES_DB: privacypal
POSTGRES_USER: privacypal
POSTGRES_PASSWORD: password
volumes:
- postgres:/var/lib/pgsql/data
restart: unless-stopped
healthcheck:
test: pg_isready -U privacypal -d privacypal || exit 1
interval: 10s
retries: 3
start_period: 10s
timeout: 5s

db-init:
image: ghcr.io/cosc-499-w2023/privacypal-init-db:0.1.0-dev
depends_on:
db:
condition: service_healthy
build: ../../web/db
networks:
- db-admin
environment:
DATABASE_URL: postgresql://privacypal:password@db:5432/privacypal
PRIVACYPAL_AUTH_MANAGER: ${PRIVACYPAL_AUTH_MANAGER:-basic}
PRIVACYPAL_USER_PROPERTY_PATH: /opt/privacypal/user.properties.csv
volumes:
- ../../web/db/sample/user.properties.csv:/opt/privacypal/user.properties.csv:z

db-viewer:
image: docker.io/dpage/pgadmin4:7
depends_on:
db:
condition: service_healthy
hostname: db-viewer
ports:
- "8989:8989"
networks:
- db-admin
environment:
PGADMIN_DEFAULT_EMAIL: admin@privacypal.io
PGADMIN_DEFAULT_PASSWORD: admin
PGADMIN_LISTEN_PORT: 8989
volumes:
- pgadmin:/var/lib/pgadmin
- ./include/servers.json:/pgadmin4/servers.json:z
restart: always
healthcheck:
test: wget --no-verbose --tries=1 --spider http://localhost:8989 || exit 1
interval: 10s
retries: 3
start_period: 10s
timeout: 5s

networks:
db-admin:

volumes:
postgres:
driver: local
pgadmin:
driver: local
67 changes: 1 addition & 66 deletions app/smoketest/compose/privacypal.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ services:
PRIVACYPAL_OUTPUT_VIDEO_DIR: /opt/privacypal/output-videos
NEXTAUTH_SECRET: a-very-secure-one
NEXTAUTH_URL: http://localhost:8080
DATABASE_URL: postgresql://privacypal:a_secure_password@db:5432/privacypal
DATABASE_URL: postgresql://privacypal:password@db:5432/privacypal
volumes:
- output_videos:/opt/privacypal/output-videos
- input_videos:/opt/privacypal/input-videos
Expand Down Expand Up @@ -58,76 +58,11 @@ services:
- input_videos:/opt/privacypal/input-videos
restart: unless-stopped

db:
image: docker.io/library/postgres:16-bullseye
networks:
- backend
- db-admin
hostname: db
expose:
- 5432
ports:
- "5432:5432"
environment:
POSTGRES_DB: privacypal
POSTGRES_USER: privacypal
POSTGRES_PASSWORD: a_secure_password
volumes:
- postgres:/var/lib/pgsql/data
restart: unless-stopped
healthcheck:
test: pg_isready -U privacypal -d privacypal || exit 1
interval: 10s
retries: 3
start_period: 10s
timeout: 5s

db-init:
image: ghcr.io/cosc-499-w2023/privacypal-init-db:0.1.0-dev
depends_on:
db:
condition: service_healthy
build: ../../web/db
networks:
- db-admin
environment:
DATABASE_URL: postgresql://privacypal:a_secure_password@db:5432/privacypal

db-viewer:
image: docker.io/dpage/pgadmin4:7
depends_on:
db:
condition: service_healthy
hostname: db-viewer
ports:
- "8989:8989"
networks:
- db-admin
environment:
PGADMIN_DEFAULT_EMAIL: admin@privacypal.io
PGADMIN_DEFAULT_PASSWORD: admin
PGADMIN_LISTEN_PORT: 8989
volumes:
- pgadmin:/var/lib/pgadmin
- ./include/servers.json:/pgadmin4/servers.json:z
restart: always
healthcheck:
test: wget --no-verbose --tries=1 --spider http://localhost:8989 || exit 1
interval: 10s
retries: 3
start_period: 10s
timeout: 5s

networks:
backend:
db-admin:

volumes:
output_videos:
driver: local
input_videos:
driver: local
postgres:
driver: local
pgadmin:
driver: local
19 changes: 16 additions & 3 deletions app/smoketest/compose/smoketest.sh
Original file line number Diff line number Diff line change
@@ -1,14 +1,27 @@
#!/bin/bash

set -ex

COMPOSE_TOOL=${COMPOSE_TOOL:-docker-compose}

FILES=(
privacypal.yaml
db.yaml
)

CMDS=()

for file in "${FILES[@]}"; do
CMDS+=( -f "${file}" )
done

cleanup() {
DOWN_FLAGS=('--remove-orphans')
local DOWN_FLAGS=('--remove-orphans')
if [ "${KEEP_VOLUMES}" != "true" ]; then
DOWN_FLAGS+=('--volumes')
fi
${COMPOSE_TOOL} \
-f privacypal.yaml \
"${CMDS[@]}" \
down "${DOWN_FLAGS[@]}"
}

Expand All @@ -17,5 +30,5 @@ trap cleanup EXIT
cleanup

${COMPOSE_TOOL} \
-f privacypal.yaml \
"${CMDS[@]}" \
up
3 changes: 3 additions & 0 deletions app/web/db/.dockerignore
Original file line number Diff line number Diff line change
Expand Up @@ -17,3 +17,6 @@ README.md
Makefile

*.log

# Sample
sample
11 changes: 6 additions & 5 deletions app/web/db/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
FROM docker.io/library/node:18-alpine
FROM docker.io/library/node:18

# Reference: https://github.com/nodejs/docker-node/tree/b4117f9333da4138b03a546ec926ef50a31506c3#nodealpine
RUN apk add --no-cache libc6-compat
ENV CONFIG_DIR=/opt/privacypal

RUN mkdir -p $CONFIG_DIR && chmod -R g=u $CONFIG_DIR

RUN adduser --system --ingroup root prisma

RUN npm install -g prisma
RUN npm install -g prisma@5.5.2

WORKDIR /app

COPY . .

USER prisma

CMD ["prisma", "migrate", "deploy"]
ENTRYPOINT ["bash", "include/entrypoint.bash"]
26 changes: 17 additions & 9 deletions app/web/db/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -7,12 +7,13 @@ SHELL := /usr/bin/env bash -o pipefail
POSTGRES_IMAGE ?= docker.io/library/postgres:16-bullseye
DATABASE ?= privacypal
DATABASE_USER ?= privacypal
DATABASE_PASSWORD ?= a_secure_password
DATABASE_PASSWORD ?= password
DATABASE_HOSTNAME ?= localhost
DATABASE_PORT ?= 5432

# Prisma schema
SCHEMA_VERSION ?= $(IMAGE_VERSION )
PRISMA_VERSION ?= 5.5.2
SCHEMA_VERSION ?= $(IMAGE_VERSION)
export DATABASE_URL=postgresql://$(DATABASE_USER):$(DATABASE_PASSWORD)@$(DATABASE_HOSTNAME):$(DATABASE_PORT)/$(DATABASE)

# Tools
Expand All @@ -31,7 +32,7 @@ DB_INIT_IMAGE ?= $(IMAGE_NAMESPACE)/$(IMAGE_NAME):$(IMAGE_VERSION)

.PHONY: help
help: ## Display this help.
@awk 'BEGIN {FS = ":.*##"; printf "\nUsage:\n make \033[36m<target>\033[0m\n"} /^[a-zA-Z_0-9-]+:.*?##/ { printf " \033[36m%-20s\033[0m %s\n", $$1, $$2 } /^##@/ { printf "\n\033[1m%s\033[0m\n", substr($$0, 5) } ' $(MAKEFILE_LIST)
@awk 'BEGIN {FS = ":.*##"; printf "\nUsage:\n make \033[36m<target>\033[0m\n"} /^[a-zA-Z_0-9-]+:.*?##/ { printf " \033[36m%-25s\033[0m %s\n", $$1, $$2 } /^##@/ { printf "\n\033[1m%s\033[0m\n", substr($$0, 5) } ' $(MAKEFILE_LIST)

##@ Build

Expand All @@ -43,14 +44,17 @@ SCHEMA_PATH ?= $(shell pwd)/schema.prisma
MIGRATION_DIR ?= $(shell pwd)/migrations
MIGRATION_SUFFIX ?= $(shell echo v$(SCHEMA_VERSION) | sed -e 's/[\.-]/_/g')


.PHONY: generate-migration
generate-migration: ## Generate latest migration DDL
- rm -r "$(MIGRATION_DIR)/$(wildcard *$(MIGRATION_SUFFIX))"
npx prisma migrate dev \
- rm -r "$(wildcard $(MIGRATION_DIR)/*$(MIGRATION_SUFFIX))"
npx prisma@$(PRISMA_VERSION) migrate dev \
--create-only \
--skip-generate \
--name $(MIGRATION_SUFFIX) \
--schema $(SCHEMA_PATH)
--schema $(SCHEMA_PATH)

##@ Smoketest

DOT_ENV ?= $(shell pwd)/.env

Expand All @@ -67,15 +71,16 @@ start-db: ## Start a postgres instance in a container for development
-e POSTGRES_PASSWORD=$(DATABASE_PASSWORD) \
-e POSTGRES_USER=$(DATABASE_USER) \
-e POSTGRES_DB=$(DATABASE) \
--rm $(POSTGRES_IMAGE)
$(POSTGRES_IMAGE)

.PHONY: remove-db
remove-db: ## Remove the postgres instance in a container for development
- $(IMAGE_BUILDER) stop postgres && $(IMAGE_BUILDER) rm postgres

##@ Smoketest

LOG_FILE ?= db-init-run.log
PRIVACYPAL_AUTH_MANAGER ?= basic
LOCAL_USER_PROPERTY_PATH ?= ./sample/user.properties.csv
PRIVACYPAL_USER_PROPERTY_PATH ?= /opt/privacypal/user.properties.csv

.PHONY: run
run: ## Run the database initialization container
Expand All @@ -84,4 +89,7 @@ run: ## Run the database initialization container
--network host \
-e NO_COLOR="true" \
-e DATABASE_URL=$(DATABASE_URL) \
-e PRIVACYPAL_AUTH_MANAGER=$(PRIVACYPAL_AUTH_MANAGER) \
-e PRIVACYPAL_USER_PROPERTY_PATH=$(PRIVACYPAL_USER_PROPERTY_PATH) \
-v "$(LOCAL_USER_PROPERTY_PATH)":"$(PRIVACYPAL_USER_PROPERTY_PATH)":z \
-it --rm $(DB_INIT_IMAGE) | tee $(LOG_FILE)
45 changes: 45 additions & 0 deletions app/web/db/include/entrypoint.bash
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
#!/usr/bin/env bash

set -e

DIR="$(dirname "$(readlink -f "$0")")"

# Fail fast when DATABASE_URL is not set.
sanitize() {
if [ -z "${DATABASE_URL}" ]; then
echo "[SEVERE][$(date)]: DATABASE_URL is missing." && exit 1
fi
}

# Initialize the database schema
generate_schema() {
prisma migrate deploy
}

# Generate user rows if necessary
generate_user_rows() {
if [ ! -f "${PRIVACYPAL_USER_PROPERTY_PATH}" ]; then
echo "[SEVERE][$(date)]: ${PRIVACYPAL_USER_PROPERTY_PATH} does not exist." && exit 1
fi

bash "$DIR/generate_insertion.bash" -f "${PRIVACYPAL_USER_PROPERTY_PATH}" -t User | prisma db execute --schema schema.prisma --stdin
}

# Prune user rows if necessary
clean_user_rows() {
prisma db execute --schema schema.prisma --file include/truncate.sql
}

export PRIVACYPAL_USER_PROPERTY_PATH="${PRIVACYPAL_USER_PROPERTY_PATH:-/opt/privacypal/user.properties.csv}"

sanitize
generate_schema

case ${PRIVACYPAL_AUTH_MANAGER} in
basic)
generate_user_rows
;;
*)
clean_user_rows
;;
esac
Loading
Loading