From f6fe57aaf1d1952b10146f8bd481d1976148e2ba Mon Sep 17 00:00:00 2001 From: Jacob Lifshay Date: Thu, 4 Jul 2024 22:03:06 -0700 Subject: [PATCH] extract config files out of setup.sh --- setup.sh | 473 +++--------------- templates/etc/docker/daemon.json | 3 + templates/etc/forgejo/app.ini | 108 ++++ templates/usr/local/bin/gitea | 3 + templates/var/discourse/containers/app.yml | 174 +++++++ templates/var/lib/stalwart-mail/cli.sh | 5 + .../var/lib/stalwart-mail/etc/config.toml | 70 +++ website_git_post_receive_hook.sh | 5 + 8 files changed, 445 insertions(+), 396 deletions(-) create mode 100644 templates/etc/docker/daemon.json create mode 100644 templates/etc/forgejo/app.ini create mode 100644 templates/usr/local/bin/gitea create mode 100644 templates/var/discourse/containers/app.yml create mode 100644 templates/var/lib/stalwart-mail/cli.sh create mode 100644 templates/var/lib/stalwart-mail/etc/config.toml create mode 100644 website_git_post_receive_hook.sh diff --git a/setup.sh b/setup.sh index 373b737..57b4f3a 100755 --- a/setup.sh +++ b/setup.sh @@ -66,27 +66,69 @@ function forgejo() docker run --rm codeberg.org/forgejo/forgejo:7 forgejo "$@" } +function write_config() +{ + local src="" dest="" vars="" new_vars=() mode="644" owner="root:root" + while (($#)); do + case "$1" in + --src) + src="$2" + shift 2 + ;; + --mode) + mode="$2" + shift 2 + ;; + --owner) + owner="$2" + shift 2 + ;; + --dest) + dest="$2" + shift 2 + ;; + --var) + [[ "$2" =~ ^([A-Za-z0-9_]+)= ]] || fatal "invalid --var argument" + vars+="\$${BASH_REMATCH[1]} " + new_vars+=("$2") + shift 2 + ;; + *) + fatal "write_config: unrecognized argument: $1" + ;; + esac + done + : "${src:?missing --src argument}" + local dest_dir temp + dest_dir="$(dirname "${dest:?missing --dest argument}")" + temp="$(umask 577 && mktemp -p "$dest_dir")" + # printf '%q ' env "${new_vars[@]}" envsubst "$vars"; + # echo "<" "$src" ">" "$temp" + env "${new_vars[@]}" envsubst "$vars" < "$src" > "$temp" || { rm -f "$temp"; exit 1; } + chmod "$mode" "$temp" || { rm -f "$temp"; exit 1; } + chown "$owner" "$temp" || { rm -f "$temp"; exit 1; } + if mv -n -T "$temp" "$dest"; then + return 0 + fi + if diff -u --label="expanded $src" "$temp" "$dest"; then + rm -f "$temp" + return 0 + else + rm -f "$temp" + fatal "config file doesn't match generated config for $dest expanded from $src" + fi +} + if [[ "$(id -u)" != 0 ]]; then fatal "must be ran as root" fi mkdir -p /var/lib/stalwart-mail apt-get update -y -q -apt-get install jq -y -q +apt-get install jq gettext-base diffutils -y -q # force using overlay2 driver so btrfs snapshots will snapshot the entire system and not miss all the docker stuff mkdir -p /etc/docker -if [[ -f /etc/docker/daemon.json ]]; then - [[ "$(jq -sc '[.[0]?["storage-driver"]?]' < /etc/docker/daemon.json)" == '["overlay2"]' ]] || - fatal '/etc/docker/daemon.json exists but `storage-driver` is not set to overlay2' -elif [[ "$(dpkg-query -W --showformat='${db:Status-Abbrev}\n' docker.io 2> /dev/null)" =~ ^$|^.[nc]' '$ ]]; then - cat > /etc/docker/daemon.json < /usr/local/bin/gitea -#!/bin/sh -exec ssh -p 2222 -o StrictHostKeyChecking=no git@127.0.0.1 "SSH_ORIGINAL_COMMAND=\"$SSH_ORIGINAL_COMMAND\" $0 $@" -EOF -chmod +x /usr/local/bin/gitea +write_config --src templates/usr/local/bin/gitea --dest /usr/local/bin/gitea --mode 755 mkdir -p /etc/forgejo rm -rf /var/www/html mkdir -p /var/www/html @@ -117,206 +155,28 @@ chmod 775 /var/www/html chown root:git /etc/forgejo chmod 770 /etc/forgejo if [[ ! -f /etc/forgejo/app.ini ]]; then - cat < /etc/forgejo/app.ini -APP_NAME = Libre-Chip.org -RUN_MODE = prod -RUN_USER = git -WORK_PATH = /data/gitea - -[repository] -ROOT = /data/git/repositories - -[repository.local] -LOCAL_COPY_PATH = /data/gitea/tmp/local-repo - -[repository.upload] -TEMP_PATH = /data/gitea/uploads - -[server] -APP_DATA_PATH = /data/gitea -DOMAIN = git.$BASE_DOMAIN_NAME -SSH_DOMAIN = git.$BASE_DOMAIN_NAME -HTTP_PORT = 3000 -ROOT_URL = https://git.$BASE_DOMAIN_NAME/ -DISABLE_SSH = false -SSH_PORT = 22 -SSH_LISTEN_PORT = 22 -LFS_START_SERVER = true -OFFLINE_MODE = false -LFS_JWT_SECRET = $(forgejo generate secret LFS_JWT_SECRET) - -[database] -PATH = /data/gitea/gitea.db -DB_TYPE = sqlite3 -HOST = localhost:3306 -NAME = gitea -USER = root -PASSWD = -LOG_SQL = false -SCHEMA = -SSL_MODE = disable - -[indexer] -ISSUE_INDEXER_PATH = /data/gitea/indexers/issues.bleve - -[session] -PROVIDER_CONFIG = /data/gitea/sessions -PROVIDER = file - -[picture] -AVATAR_UPLOAD_PATH = /data/gitea/avatars -REPOSITORY_AVATAR_UPLOAD_PATH = /data/gitea/repo-avatars - -[attachment] -PATH = /data/gitea/attachments - -[log] -MODE = console -LEVEL = info -ROOT_PATH = /data/gitea/log - -[security] -INSTALL_LOCK = true -SECRET_KEY = $(forgejo generate secret SECRET_KEY) -REVERSE_PROXY_LIMIT = 1 -REVERSE_PROXY_TRUSTED_PROXIES = * -PASSWORD_HASH_ALGO = pbkdf2_hi -DISABLE_GIT_HOOKS = false -INTERNAL_TOKEN = $(forgejo generate secret INTERNAL_TOKEN) - -[service] -DISABLE_REGISTRATION = false -REQUIRE_SIGNIN_VIEW = false -REGISTER_EMAIL_CONFIRM = true -ENABLE_NOTIFY_MAIL = true -ALLOW_ONLY_EXTERNAL_REGISTRATION = false -ENABLE_CAPTCHA = true -DEFAULT_KEEP_EMAIL_PRIVATE = false -DEFAULT_ALLOW_CREATE_ORGANIZATION = false -DEFAULT_ENABLE_TIMETRACKING = true -NO_REPLY_ADDRESS = noreply.$BASE_DOMAIN_NAME - -[lfs] -PATH = /data/git/lfs - -[mailer] -ENABLED = true -PROTOCOL = smtps -SMTP_ADDR = mail.$BASE_DOMAIN_NAME -SMTP_PORT = 465 -FROM = forgejo@$BASE_DOMAIN_NAME -USER = forgejo -PASSWD = $(random_passwd) - -[openid] -ENABLE_OPENID_SIGNIN = true -ENABLE_OPENID_SIGNUP = true - -[cron.update_checker] -ENABLED = false - -[repository.pull-request] -DEFAULT_MERGE_STYLE = merge - -[repository.signing] -DEFAULT_TRUST_MODEL = committer - -[ssh.minimum_key_sizes] -RSA = 2047 - -[oauth2] -JWT_SECRET = $(forgejo generate secret JWT_SECRET) -EOF - chown root:git /etc/forgejo/app.ini - chmod 640 /etc/forgejo/app.ini + write_config --src templates/etc/forgejo/app.ini \ + --dest /etc/forgejo/app.ini --mode 640 --owner root:git \ + --var BASE_DOMAIN_NAME="$BASE_DOMAIN_NAME" \ + --var SECRET_KEY="$(forgejo generate secret SECRET_KEY)" \ + --var INTERNAL_TOKEN="$(forgejo generate secret INTERNAL_TOKEN)" \ + --var MAIL_PASSWD="$(random_passwd)" \ + --var JWT_SECRET="$(forgejo generate secret JWT_SECRET)" \ + --var LFS_JWT_SECRET="$(forgejo generate secret LFS_JWT_SECRET)" fi mkdir -p /var/lib/stalwart-mail/etc mail_passwd="" mail_passwd_hash="" if [[ ! -f /var/lib/stalwart-mail/etc/config.toml ]]; then mail_passwd="$(random_passwd)" - cat > /var/lib/stalwart-mail/cli.sh < /var/lib/stalwart-mail/etc/config.toml < /var/discourse/containers/app.yml < /dev/null "${forgejo_api[@]}" -X 'POST' "https://git.$BASE_DOMAIN_NAME/api/v1/orgs/libre-chip/repos" -d '{"name": "website"}' > /dev/null - post_receive_hook="$(jq -csR '{content:.}' <<'EOF' -#!/bin/bash -set -e -cd /var/www/html -env -i PATH="$PATH" git fetch -env -i PATH="$PATH" git checkout -q --detach rendered -EOF - )" + post_receive_hook="$(jq -csR '{content:.}' < website_git_post_receive_hook.sh)" "${forgejo_api[@]}" -X 'PATCH' "https://git.$BASE_DOMAIN_NAME/api/v1/repos/libre-chip/website/hooks/git/post-receive" -d "$post_receive_hook" > /dev/null fi ( diff --git a/templates/etc/docker/daemon.json b/templates/etc/docker/daemon.json new file mode 100644 index 0000000..a442642 --- /dev/null +++ b/templates/etc/docker/daemon.json @@ -0,0 +1,3 @@ +{ + "storage-driver": "overlay2" +} \ No newline at end of file diff --git a/templates/etc/forgejo/app.ini b/templates/etc/forgejo/app.ini new file mode 100644 index 0000000..20f1195 --- /dev/null +++ b/templates/etc/forgejo/app.ini @@ -0,0 +1,108 @@ +APP_NAME = Libre-Chip.org +RUN_MODE = prod +RUN_USER = git +WORK_PATH = /data/gitea + +[repository] +ROOT = /data/git/repositories + +[repository.local] +LOCAL_COPY_PATH = /data/gitea/tmp/local-repo + +[repository.upload] +TEMP_PATH = /data/gitea/uploads + +[server] +APP_DATA_PATH = /data/gitea +DOMAIN = git.$BASE_DOMAIN_NAME +SSH_DOMAIN = git.$BASE_DOMAIN_NAME +HTTP_PORT = 3000 +ROOT_URL = https://git.$BASE_DOMAIN_NAME/ +DISABLE_SSH = false +SSH_PORT = 22 +SSH_LISTEN_PORT = 22 +LFS_START_SERVER = true +OFFLINE_MODE = false +LFS_JWT_SECRET = $(forgejo generate secret LFS_JWT_SECRET) + +[database] +PATH = /data/gitea/gitea.db +DB_TYPE = sqlite3 +HOST = localhost:3306 +NAME = gitea +USER = root +PASSWD = +LOG_SQL = false +SCHEMA = +SSL_MODE = disable + +[indexer] +ISSUE_INDEXER_PATH = /data/gitea/indexers/issues.bleve + +[session] +PROVIDER_CONFIG = /data/gitea/sessions +PROVIDER = file + +[picture] +AVATAR_UPLOAD_PATH = /data/gitea/avatars +REPOSITORY_AVATAR_UPLOAD_PATH = /data/gitea/repo-avatars + +[attachment] +PATH = /data/gitea/attachments + +[log] +MODE = console +LEVEL = info +ROOT_PATH = /data/gitea/log + +[security] +INSTALL_LOCK = true +SECRET_KEY = $SECRET_KEY +REVERSE_PROXY_LIMIT = 1 +REVERSE_PROXY_TRUSTED_PROXIES = * +PASSWORD_HASH_ALGO = pbkdf2_hi +DISABLE_GIT_HOOKS = false +INTERNAL_TOKEN = $INTERNAL_TOKEN + +[service] +DISABLE_REGISTRATION = false +REQUIRE_SIGNIN_VIEW = false +REGISTER_EMAIL_CONFIRM = true +ENABLE_NOTIFY_MAIL = true +ALLOW_ONLY_EXTERNAL_REGISTRATION = false +ENABLE_CAPTCHA = true +DEFAULT_KEEP_EMAIL_PRIVATE = false +DEFAULT_ALLOW_CREATE_ORGANIZATION = false +DEFAULT_ENABLE_TIMETRACKING = true +NO_REPLY_ADDRESS = noreply.$BASE_DOMAIN_NAME + +[lfs] +PATH = /data/git/lfs + +[mailer] +ENABLED = true +PROTOCOL = smtps +SMTP_ADDR = mail.$BASE_DOMAIN_NAME +SMTP_PORT = 465 +FROM = forgejo@$BASE_DOMAIN_NAME +USER = forgejo +PASSWD = $MAIL_PASSWD + +[openid] +ENABLE_OPENID_SIGNIN = true +ENABLE_OPENID_SIGNUP = true + +[cron.update_checker] +ENABLED = false + +[repository.pull-request] +DEFAULT_MERGE_STYLE = merge + +[repository.signing] +DEFAULT_TRUST_MODEL = committer + +[ssh.minimum_key_sizes] +RSA = 2047 + +[oauth2] +JWT_SECRET = $JWT_SECRET diff --git a/templates/usr/local/bin/gitea b/templates/usr/local/bin/gitea new file mode 100644 index 0000000..40f0433 --- /dev/null +++ b/templates/usr/local/bin/gitea @@ -0,0 +1,3 @@ +#!/bin/bash +printf -v args '%q ' "$SSH_ORIGINAL_COMMAND" "$0" "$@" +exec ssh -p 2222 -o StrictHostKeyChecking=no git@127.0.0.1 "SSH_ORIGINAL_COMMAND=$args" diff --git a/templates/var/discourse/containers/app.yml b/templates/var/discourse/containers/app.yml new file mode 100644 index 0000000..9c46f9b --- /dev/null +++ b/templates/var/discourse/containers/app.yml @@ -0,0 +1,174 @@ +## this is the all-in-one, standalone Discourse Docker container template +## +## After making changes to this file, you MUST rebuild +## /var/discourse/launcher rebuild app +## +## Based on https://meta.discourse.org/t/run-other-websites-on-the-same-machine-as-discourse/17247 + +templates: + - "templates/postgres.template.yml" + - "templates/redis.template.yml" + - "templates/web.template.yml" + ## Uncomment the next line to enable the IPv6 listener + #- "templates/web.ipv6.template.yml" + - "templates/web.ratelimited.template.yml" + - "templates/web.socketed.template.yml" + ## Uncomment these two lines if you wish to add Lets Encrypt (https) + #- "templates/web.ssl.template.yml" + #- "templates/web.letsencrypt.ssl.template.yml" + +## which TCP/IP ports should this container expose? +## If you want Discourse to share a port with another webserver like Apache or nginx, +## see https://meta.discourse.org/t/17247 for details +#expose: +# - "80:80" # http +# - "443:443" # https + +params: + db_default_text_search_config: "pg_catalog.english" + + ## Set db_shared_buffers to a max of 25% of the total memory. + ## will be set automatically by bootstrap based on detected RAM, or you can override + db_shared_buffers: "512MB" + + ## can improve sorting performance, but adds memory usage per-connection + #db_work_mem: "40MB" + + ## Which Git revision should this container use? (default: tests-passed) + #version: tests-passed + +env: + LC_ALL: en_US.UTF-8 + LANG: en_US.UTF-8 + LANGUAGE: en_US.UTF-8 + # DISCOURSE_DEFAULT_LOCALE: en + + ## How many concurrent web requests are supported? Depends on memory and CPU cores. + ## will be set automatically by bootstrap based on detected CPUs, or you can override + UNICORN_WORKERS: 4 + + ## TODO: The domain name this Discourse instance will respond to + ## Required. Discourse will not work with a bare IP number. + DISCOURSE_HOSTNAME: forum.${BASE_DOMAIN_NAME} + + ## Uncomment if you want the container to be started with the same + ## hostname (-h option) as specified above (default "$hostname-$config") + #DOCKER_USE_HOSTNAME: true + + ## TODO: List of comma delimited emails that will be made admin and developer + ## on initial signup example 'user1@example.com,user2@example.com' + DISCOURSE_DEVELOPER_EMAILS: 'postmaster@${BASE_DOMAIN_NAME}' + + ## TODO: The SMTP mail server used to validate new accounts and send notifications + # SMTP ADDRESS, username, and password are required + # WARNING the char '#' in SMTP password can cause problems! + DISCOURSE_SMTP_ADDRESS: ${BASE_DOMAIN_NAME} + DISCOURSE_SMTP_PORT: 587 + DISCOURSE_SMTP_USER_NAME: forum-noreply + DISCOURSE_SMTP_PASSWORD: "${forum_smtp_passwd}" + #DISCOURSE_SMTP_ENABLE_START_TLS: true # (optional, default true) + DISCOURSE_SMTP_DOMAIN: ${BASE_DOMAIN_NAME} + DISCOURSE_NOTIFICATION_EMAIL: forum-noreply@${BASE_DOMAIN_NAME} + + ## If you added the Lets Encrypt template, uncomment below to get a free SSL certificate + #LETSENCRYPT_ACCOUNT_EMAIL: me@example.com + + ## The http or https CDN address for this Discourse instance (configured to pull) + ## see https://meta.discourse.org/t/14857 for details + #DISCOURSE_CDN_URL: https://discourse-cdn.example.com + + ## The maxmind geolocation IP account ID and license key for IP address lookups + ## see https://meta.discourse.org/t/-/173941 for details + #DISCOURSE_MAXMIND_ACCOUNT_ID: 123456 + #DISCOURSE_MAXMIND_LICENSE_KEY: 1234567890123456 + +## The Docker container is stateless; all data is stored in /shared +volumes: + - volume: + host: /var/discourse/shared/standalone + guest: /shared + - volume: + host: /var/discourse/shared/standalone/log/var-log + guest: /var/log + - volume: + host: /usr/local/share/ca-certificates + guest: /usr/local/share/ca-certificates:ro + +## Plugins go here +## see https://meta.discourse.org/t/19157 for details +hooks: + after_code: + - exec: + cd: $home/plugins + cmd: + - git clone https://github.com/discourse/docker_manager.git + +## Any custom commands to run after building +run: + - exec: echo "Beginning of custom commands" + - exec: |- + if rails r 'exit(1) if User.find_by_email("postmaster@${BASE_DOMAIN_NAME}")'; then + rails r "SiteSetting.pop3_polling_openssl_verify = false" || exit + rails site_settings:import <