From 1b83a2b0660b745c1f9bdd2d8e25517be1caac7b Mon Sep 17 00:00:00 2001 From: Pranav C Date: Mon, 12 Feb 2024 11:52:21 +0530 Subject: [PATCH] chore: add docker-compose setup script Signed-off-by: Pranav C --- docker-compose/setup-script/noco.sh | 389 ++++++++++++++++++++++++++++ 1 file changed, 389 insertions(+) create mode 100644 docker-compose/setup-script/noco.sh diff --git a/docker-compose/setup-script/noco.sh b/docker-compose/setup-script/noco.sh new file mode 100644 index 0000000000..90d92ba8fb --- /dev/null +++ b/docker-compose/setup-script/noco.sh @@ -0,0 +1,389 @@ +#!/bin/bash +# set -x + +# ****************************************************************************** +# ***************** HELPER FUNCTIONS START ********************************* + +# Function to URL encode special characters in a string +urlencode() { + local string="$1" + local strlen=${#string} + local encoded="" + local pos c o + + for (( pos=0 ; pos /dev/null; then + echo " | Error: $tool is not installed. Please install it before proceeding." + PRE_REQ=1 + fi +done + +# e. Check if NocoDB is already installed and its expected version +# echo "Checking if NocoDB is already installed and its expected version..." +# Replace the following command with the actual command to check NocoDB installation and version +# Example: nocodb_version=$(command_to_get_nocodb_version) +# echo "NocoDB version: $nocodb_install_version" + +# f. Port mapping check +echo " | Checking port accessibility..." +for port in "${REQUIRED_PORTS[@]}"; do + if lsof -Pi :$port -sTCP:LISTEN -t >/dev/null; then + echo " | WARNING: Port $port is in use. Please make sure it is free." >&2 + PRE_REQ=1 + else + echo " | Port $port is free." + fi +done + +echo "** System check completed successfully. **" + + +# Define an array to store the messages to be printed at the end +message_arr=() + +# generate a folder for the docker-compose file which is not existing and do the setup within the folder +# Define the folder name +FOLDER_NAME="nocodb_$(date +"%Y%m%d_%H%M%S")" + +# prompt for custom folder name and if left empty skip +#echo "Enter a custom folder name or press Enter to use the default folder name ($FOLDER_NAME): " +#read CUSTOM_FOLDER_NAME + +message_arr+=("Setup folder: $FOLDER_NAME") + +if [ -n "$CUSTOM_FOLDER_NAME" ]; then + FOLDER_NAME="$CUSTOM_FOLDER_NAME" +fi + + +# Create the folder +mkdir -p "$FOLDER_NAME" + +# Navigate into the folder +cd "$FOLDER_NAME" || exit + +# ******************** SYSTEM REQUIREMENTS CHECK END ************************** +# ****************************************************************************** + + + +# ******************** INPUTS FROM USER START ******************************** +# ****************************************************************************** + +echo "Choose Community or Enterprise Edition [CE/EE] (default: CE): " +read EDITION + +echo "Do you want to configure SSL [Y/N] (default: N): " +read SSL_ENABLED + + +if [ -n "$SSL_ENABLED" ] && { [ "$SSL_ENABLED" = "Y" ] || [ "$SSL_ENABLED" = "y" ]; }; then + SSL_ENABLED='y' + echo "Enter the domain name for the SSL certificate: " + read DOMAIN_NAME + if [ -z "$DOMAIN_NAME" ]; then + echo "Domain name is required for SSL configuration" + exit 1 + fi + message_arr+=("Domain: $DOMAIN_NAME") +else +# prompt for ip address and if left empty use localhost + echo "Enter the IP address or domain name for the NocoDB instance (default: localhost): " + read DOMAIN_NAME + if [ -z "$DOMAIN_NAME" ]; then + DOMAIN_NAME="localhost" + fi +fi + +if [ -n "$EDITION" ] && { [ "$EDITION" = "EE" ] || [ "$EDITION" = "ee" ]; }; then + echo "Enter the NocoDB license key: " + read LICENSE_KEY + if [ -z "$LICENSE_KEY" ]; then + echo "License key is required for Enterprise Edition installation" + exit 1 + fi + message_arr+=("License key: $LICENSE_KEY") +fi + +echo "Do you want to enabled Watchtower for automatic updates [Y/N] (default: Y): " +read WATCHTOWER_ENABLED + +if [ -z "$WATCHTOWER_ENABLED" ] || { [ "$WATCHTOWER_ENABLED" != "N" ] && [ "$WATCHTOWER_ENABLED" != "n" ]; }; then + message_arr+=("Watchtower: Enabled") +else + message_arr+=("Watchtower: Disabled") +fi + + +# ****************************************************************************** +# *********************** INPUTS FROM USER END ******************************** + + +# ****************************************************************************** +# *************************** SETUP START ************************************* + +# Generate a strong random password for PostgreSQL +#STRONG_PASSWORD=$(cat /dev/urandom | tr -dc '[:alnum:]' | head -c 20) +#STRONG_PASSWORD=$(openssl rand -base64 32) +STRONG_PASSWORD=$(openssl rand -base64 48 | tr -dc 'a-zA-Z0-9!@#$%^&*()-_+=' | head -c 32) +# Encode special characters in the password for JDBC URL usage +ENCODED_PASSWORD=$(urlencode "$STRONG_PASSWORD") + +IMAGE="nocodb/nocodb:latest"; + +# Determine the Docker image to use based on the edition +if [ -n "$EDITION" ] && { [ "$EDITION" = "EE" ] || [ "$EDITION" = "ee" ]; }; then + echo "Using the NocoDB Enterprise Edition image" + IMAGE="nocodb/nocodb-ee:latest" + DATABASE_URL="DATABASE_URL=postgres://postgres:${ENCODED_PASSWORD}@db:5432/nocodb" +else + # use NC_DB url until the issue with DATABASE_URL is resolved(encoding) + DATABASE_URL="NC_DB=pg://db:5432?d=nocodb&user=postgres&password=${ENCODED_PASSWORD}" +fi + + +message_arr+=("Docker image: $IMAGE") + +# Write the Docker Compose file with the updated password +cat < docker-compose.yml +version: '3' + +services: + nocodb: + image: ${IMAGE} + env_file: docker.env + depends_on: + - db + restart: unless-stopped + volumes: + - ./nocodb:/usr/app/data + labels: + - "com.centurylinklabs.watchtower.enable=true" + db: + image: postgres:latest + env_file: docker.env + volumes: + - ./postgres:/var/lib/postgresql/data + restart: unless-stopped + + nginx: + image: nginx:latest + volumes: + - ./nginx:/etc/nginx/conf.d +EOF + +if [ "$SSL_ENABLED" = 'y' ]; then + cat <> docker-compose.yml + - webroot:/var/www/certbot + - ./letsencrypt:/etc/letsencrypt + - letsencrypt-lib:/var/lib/letsencrypt +EOF +fi +cat <> docker-compose.yml + ports: + - "80:80" + - "443:443" + depends_on: + - nocodb + restart: unless-stopped +EOF + +if [ "$SSL_ENABLED" = 'y' ]; then + cat <> docker-compose.yml + certbot: + image: certbot/certbot + volumes: + - ./letsencrypt:/etc/letsencrypt + - letsencrypt-lib:/var/lib/letsencrypt + - webroot:/var/www/certbot + entrypoint: "/bin/sh -c 'trap exit TERM; while :; do certbot renew; sleep 12h & wait \$\${!}; done;'" + depends_on: + - nginx + restart: unless-stopped +EOF +fi + +if [ -z "$WATCHTOWER_ENABLED" ] || { [ "$WATCHTOWER_ENABLED" != "N" ] && [ "$WATCHTOWER_ENABLED" != "n" ]; }; then +cat <> docker-compose.yml + watchtower: + image: containrrr/watchtower + volumes: + - /var/run/docker.sock:/var/run/docker.sock + command: --schedule "0 2 * * 6" --cleanup + restart: unless-stopped +EOF +fi + +if [ "$SSL_ENABLED" = 'y' ]; then + cat <> docker-compose.yml +volumes: + letsencrypt-lib: + webroot: +EOF +fi + +# Write the docker.env file +cat < docker.env +POSTGRES_DB=nocodb +POSTGRES_USER=postgres +POSTGRES_PASSWORD=${STRONG_PASSWORD} +$DATABASE_URL +NC_LICENSE_KEY=${LICENSE_KEY} +EOF + +mkdir -p ./nginx + +# Create nginx config with the provided domain name +cat > ./nginx/default.conf <> ./nginx/default.conf <> ./nginx/default.conf <> ./nginx/default.conf <> ./nginx/default.conf < ./nginx-post-config/default.conf <