diff --git a/.env.example b/.env.example index 5b2c0e2..f62751d 100644 --- a/.env.example +++ b/.env.example @@ -177,6 +177,10 @@ RUN_N8N_IMPORT= # n8n configuration ############ +# n8n version (used for both n8n and task runner images) +# Update this when upgrading n8n to ensure runner version matches +N8N_VERSION=stable + # Number of n8n worker-runner pairs to generate. # Each worker gets its own dedicated task runner sidecar. # After changing, run: bash scripts/generate_n8n_workers.sh diff --git a/README.md b/README.md index ad4c9be..a56271f 100644 --- a/README.md +++ b/README.md @@ -129,9 +129,8 @@ During the installation, the script will prompt you for: 2. Your **email address** (Required, used for service logins like Flowise, Supabase dashboard, Grafana, and for SSL certificate registration with Let's Encrypt). 3. An optional **OpenAI API key** (Not required. If provided, it can be used by Supabase AI features and Crawl4ai. Press Enter to skip). 4. Whether you want to **import ~300 ready-made n8n community workflows** (y/n, Optional. This can take 20-30 minutes, depending on your server and network speed). -5. The **number of n8n workers** you want to run (Required, e.g., 1, 2, 3, 4. This determines how many workflows can be processed in parallel. Defaults to 1 if not specified). -6. The **number of n8n task runners** you want to run (Required, e.g., 1, 2, 3. Task runners execute JavaScript and Python Code nodes. Defaults to 1 if not specified). -7. A **Service Selection Wizard** will then appear, allowing you to choose which of the available services (like Flowise, Supabase, Qdrant, Open WebUI, etc.) you want to deploy. Core services (Caddy, Postgres, Redis) will be set up to support your selections. +5. The **number of n8n workers** you want to run (Required, e.g., 1, 2, 3, 4. This determines how many workflows can be processed in parallel. Each worker automatically gets its own dedicated task runner sidecar for executing Code nodes. Defaults to 1 if not specified). +6. A **Service Selection Wizard** will then appear, allowing you to choose which of the available services (like Flowise, Supabase, Qdrant, Open WebUI, etc.) you want to deploy. Core services (Caddy, Postgres, Redis) will be set up to support your selections. Upon successful completion, the script will display a summary report. This report contains the access URLs and credentials for the deployed services. **Save this information in a safe place!** diff --git a/docker-compose.yml b/docker-compose.yml index 11a17c6..f0596c5 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -38,6 +38,8 @@ x-n8n: &service-n8n build: context: ./n8n pull: true + args: + N8N_VERSION: ${N8N_VERSION:-stable} environment: &service-n8n-env DB_POSTGRESDB_DATABASE: postgres DB_POSTGRESDB_HOST: postgres @@ -109,7 +111,7 @@ x-init-ollama: &init-ollama # Worker-runner anchor for sidecar pattern (runner connects to worker via localhost) x-n8n-worker-runner: &service-n8n-worker-runner - image: n8nio/runners:2.0.0 + image: n8nio/runners:${N8N_VERSION:-stable} environment: N8N_RUNNERS_AUTH_TOKEN: ${N8N_RUNNERS_AUTH_TOKEN} N8N_RUNNERS_AUTO_SHUTDOWN_TIMEOUT: 15 @@ -173,6 +175,12 @@ services: - n8n_storage:/home/node/.n8n - ./n8n/backup:/backup - ./shared:/data/shared + healthcheck: + test: ["CMD-SHELL", "wget -qO- http://localhost:5678/healthz || exit 1"] + interval: 30s + timeout: 10s + retries: 5 + start_period: 30s depends_on: n8n-import: condition: service_completed_successfully @@ -186,6 +194,12 @@ services: volumes: - n8n_storage:/home/node/.n8n - ./shared:/data/shared + healthcheck: + test: ["CMD-SHELL", "wget -qO- http://localhost:5678/healthz || exit 1"] + interval: 30s + timeout: 10s + retries: 5 + start_period: 30s n8n-runner-template: <<: *service-n8n-worker-runner diff --git a/n8n/Dockerfile b/n8n/Dockerfile index 547866a..e95d41e 100644 --- a/n8n/Dockerfile +++ b/n8n/Dockerfile @@ -1,4 +1,5 @@ -FROM n8nio/n8n:2.0.0 +ARG N8N_VERSION=stable +FROM n8nio/n8n:${N8N_VERSION} USER root RUN apk add --no-cache ffmpeg diff --git a/scripts/03_generate_secrets.sh b/scripts/03_generate_secrets.sh index cdd9d84..9ffa9cd 100644 --- a/scripts/03_generate_secrets.sh +++ b/scripts/03_generate_secrets.sh @@ -290,7 +290,6 @@ found_vars["SEARXNG_USERNAME"]=0 found_vars["OPENAI_API_KEY"]=0 found_vars["LANGFUSE_INIT_USER_EMAIL"]=0 found_vars["N8N_WORKER_COUNT"]=0 -found_vars["N8N_RUNNER_COUNT"]=0 found_vars["WEAVIATE_USERNAME"]=0 found_vars["NEO4J_AUTH_USERNAME"]=0 found_vars["COMFYUI_USERNAME"]=0 @@ -347,7 +346,7 @@ while IFS= read -r line || [[ -n "$line" ]]; do # This 'else' block is for lines from template not covered by existing values or VARS_TO_GENERATE. # Check if it is one of the user input vars - these are handled by found_vars later if not in template. is_user_input_var=0 # Reset for each line - user_input_vars=("FLOWISE_USERNAME" "DASHBOARD_USERNAME" "LETSENCRYPT_EMAIL" "RUN_N8N_IMPORT" "PROMETHEUS_USERNAME" "SEARXNG_USERNAME" "OPENAI_API_KEY" "LANGFUSE_INIT_USER_EMAIL" "N8N_WORKER_COUNT" "N8N_RUNNER_COUNT" "WEAVIATE_USERNAME" "NEO4J_AUTH_USERNAME" "COMFYUI_USERNAME" "RAGAPP_USERNAME" "PADDLEOCR_USERNAME" "LT_USERNAME" "LIGHTRAG_USERNAME" "WAHA_DASHBOARD_USERNAME" "WHATSAPP_SWAGGER_USERNAME") + user_input_vars=("FLOWISE_USERNAME" "DASHBOARD_USERNAME" "LETSENCRYPT_EMAIL" "RUN_N8N_IMPORT" "PROMETHEUS_USERNAME" "SEARXNG_USERNAME" "OPENAI_API_KEY" "LANGFUSE_INIT_USER_EMAIL" "N8N_WORKER_COUNT" "WEAVIATE_USERNAME" "NEO4J_AUTH_USERNAME" "COMFYUI_USERNAME" "RAGAPP_USERNAME" "PADDLEOCR_USERNAME" "LT_USERNAME" "LIGHTRAG_USERNAME" "WAHA_DASHBOARD_USERNAME" "WHATSAPP_SWAGGER_USERNAME") for uivar in "${user_input_vars[@]}"; do if [[ "$varName" == "$uivar" ]]; then is_user_input_var=1 @@ -429,7 +428,7 @@ if [[ -z "${generated_values[SERVICE_ROLE_KEY]}" ]]; then fi # Add any custom variables that weren't found in the template -for var in "FLOWISE_USERNAME" "DASHBOARD_USERNAME" "LETSENCRYPT_EMAIL" "RUN_N8N_IMPORT" "OPENAI_API_KEY" "PROMETHEUS_USERNAME" "SEARXNG_USERNAME" "LANGFUSE_INIT_USER_EMAIL" "N8N_WORKER_COUNT" "N8N_RUNNER_COUNT" "WEAVIATE_USERNAME" "NEO4J_AUTH_USERNAME" "COMFYUI_USERNAME" "RAGAPP_USERNAME" "PADDLEOCR_USERNAME" "LT_USERNAME" "LIGHTRAG_USERNAME" "WAHA_DASHBOARD_USERNAME" "WHATSAPP_SWAGGER_USERNAME" "DOCLING_USERNAME"; do +for var in "FLOWISE_USERNAME" "DASHBOARD_USERNAME" "LETSENCRYPT_EMAIL" "RUN_N8N_IMPORT" "OPENAI_API_KEY" "PROMETHEUS_USERNAME" "SEARXNG_USERNAME" "LANGFUSE_INIT_USER_EMAIL" "N8N_WORKER_COUNT" "WEAVIATE_USERNAME" "NEO4J_AUTH_USERNAME" "COMFYUI_USERNAME" "RAGAPP_USERNAME" "PADDLEOCR_USERNAME" "LT_USERNAME" "LIGHTRAG_USERNAME" "WAHA_DASHBOARD_USERNAME" "WHATSAPP_SWAGGER_USERNAME" "DOCLING_USERNAME"; do if [[ ${found_vars["$var"]} -eq 0 && -v generated_values["$var"] ]]; then # Before appending, check if it's already in TMP_ENV_FILE to avoid duplicates if ! grep -q -E "^${var}=" "$TMP_ENV_FILE"; then diff --git a/scripts/generate_n8n_workers.sh b/scripts/generate_n8n_workers.sh index 949a1b5..3092d82 100755 --- a/scripts/generate_n8n_workers.sh +++ b/scripts/generate_n8n_workers.sh @@ -21,7 +21,8 @@ fi # Загрузить N8N_WORKER_COUNT из .env если не задан if [[ -z "${N8N_WORKER_COUNT:-}" ]] && [[ -f "$PROJECT_DIR/.env" ]]; then - N8N_WORKER_COUNT=$(grep -E "^N8N_WORKER_COUNT=" "$PROJECT_DIR/.env" | cut -d'=' -f2 || echo "1") + # Strip quotes (single and double) from the value + N8N_WORKER_COUNT=$(grep -E "^N8N_WORKER_COUNT=" "$PROJECT_DIR/.env" | cut -d'=' -f2 | tr -d '"'"'" || echo "1") fi N8N_WORKER_COUNT=${N8N_WORKER_COUNT:-1} @@ -56,7 +57,7 @@ cat >> "$OUTPUT_FILE" << EOF restart: unless-stopped depends_on: n8n: - condition: service_started + condition: service_healthy redis: condition: service_healthy postgres: @@ -72,7 +73,7 @@ cat >> "$OUTPUT_FILE" << EOF network_mode: "service:n8n-worker-$i" depends_on: n8n-worker-$i: - condition: service_started + condition: service_healthy EOF done