diff --git a/.dockerignore b/.dockerignore
index fb85e2ca..2f4b4b61 100644
--- a/.dockerignore
+++ b/.dockerignore
@@ -10,3 +10,5 @@ docs/
*.sln
*.njsproj
*.md
+examples
+tests
\ No newline at end of file
diff --git a/.github/workflows/docker.yml b/.github/workflows/docker-alpine.yml
similarity index 99%
rename from .github/workflows/docker.yml
rename to .github/workflows/docker-alpine.yml
index 2e5b7ad6..75caaef9 100644
--- a/.github/workflows/docker.yml
+++ b/.github/workflows/docker-alpine.yml
@@ -1,9 +1,9 @@
-name: Docker-Builder
+name: Docker-Builder-Alpine
on:
workflow_dispatch:
schedule:
- - cron: '2 0 * * *' # Daily at 00:02 UTC
+ - cron: '0 0 * * *' # Daily at 00:00 UTC
release:
types: [ published ]
@@ -95,7 +95,7 @@ jobs:
.
build-arm64:
- runs-on: ubuntu-22.04-arm
+ runs-on: ubuntu-24.04-arm
needs: translate
strategy:
fail-fast: false
diff --git a/.github/workflows/docker-debian.yml b/.github/workflows/docker-debian.yml
new file mode 100644
index 00000000..5a862727
--- /dev/null
+++ b/.github/workflows/docker-debian.yml
@@ -0,0 +1,230 @@
+name: Docker-Builder-Debian
+
+on:
+ workflow_dispatch:
+ schedule:
+ - cron: '0 1 * * *' # Daily at 01:00 UTC (I think)
+ release:
+ types: [ published ]
+
+jobs:
+
+ translate:
+ runs-on: ubuntu-24.04
+ name: Run Translations
+ steps:
+ - name: Checkout repository
+ uses: actions/checkout@v5
+ - name: Set up Node.js
+ uses: actions/setup-node@v6
+ with:
+ node-version: "lts/*"
+ - name: Run translate.js (ignore errors)
+ run: node translate.js || true
+ working-directory: translate
+ - name: Run translate extractall
+ run: node translate extractall
+ working-directory: translate
+ - name: Run translate.js minifyall
+ run: node translate.js minifyall
+ working-directory: translate
+ - name: Run translate.js translateall
+ run: node translate.js translateall
+ working-directory: translate
+ - name: Upload repo with translations
+ uses: actions/upload-artifact@v5
+ with:
+ name: repo-with-translations
+ path: .
+
+ build-amd64:
+ runs-on: ubuntu-24.04
+ needs: translate
+ strategy:
+ fail-fast: false
+ max-parallel: 3
+ matrix:
+ variant: [mongodb, postgresql, mariadb, all, slim]
+ name: Build Docker Image (amd64-${{ matrix.variant }})
+ steps:
+ - name: Download repo artifact
+ uses: actions/download-artifact@v5
+ with:
+ name: repo-with-translations
+ - name: Set up QEMU
+ uses: docker/setup-qemu-action@v3
+ with:
+ cache-image: false
+ platforms: amd64
+ - name: Set up Docker Buildx
+ uses: docker/setup-buildx-action@v3
+ with:
+ cache-binary: false
+ - name: Log in to GitHub Container Registry
+ uses: docker/login-action@v3
+ with:
+ registry: ghcr.io
+ username: ${{ github.repository_owner }}
+ password: ${{ secrets.MY_TOKEN || secrets.GITHUB_TOKEN }}
+ - name: Build and push Docker image (amd64-${{ matrix.variant }})
+ run: |
+ REPO_OWNER_LC="$(echo "${{ github.repository_owner }}" | tr '[:upper:]' '[:lower:]')"
+ case "${{ matrix.variant }}" in
+ mongodb)
+ MONGODB=YES; POSTGRESQL=NO; MARIADB=NO; TAG="-amd64-mongodb-debian";;
+ postgresql)
+ MONGODB=NO; POSTGRESQL=YES; MARIADB=NO; TAG="-amd64-postgresql-debian";;
+ mariadb)
+ MONGODB=NO; POSTGRESQL=NO; MARIADB=YES; TAG="-amd64-mariadb-debian";;
+ all)
+ MONGODB=YES; POSTGRESQL=YES; MARIADB=YES; TAG="-amd64-debian";;
+ slim)
+ MONGODB=NO; POSTGRESQL=NO; MARIADB=NO; TAG="-amd64-slim-debian";;
+ esac
+ docker buildx build \
+ --platform linux/amd64 \
+ --build-arg INCLUDE_MONGODB_TOOLS=$MONGODB \
+ --build-arg INCLUDE_POSTGRESQL_TOOLS=$POSTGRESQL \
+ --build-arg INCLUDE_MARIADB_TOOLS=$MARIADB \
+ --build-arg DISABLE_MINIFY=yes \
+ --build-arg DISABLE_TRANSLATE=yes \
+ --build-arg DISABLE_EXTRACT=yes \
+ --build-arg PREINSTALL_LIBS=true \
+ -f docker/Dockerfile-debian \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}$TAG \
+ --push \
+ .
+
+ build-arm64:
+ runs-on: ubuntu-24.04-arm
+ needs: translate
+ strategy:
+ fail-fast: false
+ max-parallel: 3
+ matrix:
+ variant: [mongodb, postgresql, mariadb, all, slim]
+ name: Build Docker Image (arm64-${{ matrix.variant }})
+ steps:
+ - name: Download repo artifact
+ uses: actions/download-artifact@v5
+ with:
+ name: repo-with-translations
+ - name: Set up QEMU
+ uses: docker/setup-qemu-action@v3
+ with:
+ cache-image: false
+ platforms: arm64
+ - name: Set up Docker Buildx
+ uses: docker/setup-buildx-action@v3
+ with:
+ cache-binary: false
+ - name: Log in to GitHub Container Registry
+ uses: docker/login-action@v3
+ with:
+ registry: ghcr.io
+ username: ${{ github.repository_owner }}
+ password: ${{ secrets.MY_TOKEN || secrets.GITHUB_TOKEN }}
+ - name: Build and push Docker image (arm64-${{ matrix.variant }})
+ run: |
+ REPO_OWNER_LC="$(echo "${{ github.repository_owner }}" | tr '[:upper:]' '[:lower:]')"
+ case "${{ matrix.variant }}" in
+ mongodb)
+ MONGODB=YES; POSTGRESQL=NO; MARIADB=NO; TAG="-arm64-mongodb-debian";;
+ postgresql)
+ MONGODB=NO; POSTGRESQL=YES; MARIADB=NO; TAG="-arm64-postgresql-debian";;
+ mariadb)
+ MONGODB=NO; POSTGRESQL=NO; MARIADB=YES; TAG="-arm64-mariadb-debian";;
+ all)
+ MONGODB=YES; POSTGRESQL=YES; MARIADB=YES; TAG="-arm64-debian";;
+ slim)
+ MONGODB=NO; POSTGRESQL=NO; MARIADB=NO; TAG="-arm64-slim-debian";;
+ esac
+ docker buildx build \
+ --platform linux/arm64 \
+ --build-arg INCLUDE_MONGODB_TOOLS=$MONGODB \
+ --build-arg INCLUDE_POSTGRESQL_TOOLS=$POSTGRESQL \
+ --build-arg INCLUDE_MARIADB_TOOLS=$MARIADB \
+ --build-arg DISABLE_MINIFY=yes \
+ --build-arg DISABLE_TRANSLATE=yes \
+ --build-arg DISABLE_EXTRACT=yes \
+ --build-arg PREINSTALL_LIBS=true \
+ -f docker/Dockerfile-debian \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}$TAG \
+ --push \
+ .
+
+ merge-manifest:
+ runs-on: ubuntu-24.04
+ needs:
+ - translate
+ - build-amd64
+ - build-arm64
+ name: Create and Push Multi-Arch Manifest
+ steps:
+ - name: Set up Docker Buildx
+ uses: docker/setup-buildx-action@v3
+ with:
+ cache-binary: false
+ - name: Log in to GitHub Container Registry
+ uses: docker/login-action@v3
+ with:
+ registry: ghcr.io
+ username: ${{ github.repository_owner }}
+ password: ${{ secrets.MY_TOKEN || secrets.GITHUB_TOKEN }}
+ - name: Create and push multi-arch manifests for all variants
+ run: |
+ REPO_OWNER_LC="$(echo "${{ github.repository_owner }}" | tr '[:upper:]' '[:lower:]')"
+ # mongodb
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-mongodb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-mongodb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-mongodb-debian \
+ # postgresql
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-postgresql-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-postgresql-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-postgresql-debian \
+ # mariadb
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-mariadb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-mariadb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-mariadb-debian \
+ # all (no suffix)
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-debian \
+ # slim
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-slim-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-slim-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-slim-debian \
+ - name: Create and push 'latest' tags (releases only)
+ if: github.event_name == 'release'
+ run: |
+ REPO_OWNER_LC="$(echo "${{ github.repository_owner }}" | tr '[:upper:]' '[:lower:]')"
+ # latest-mongodb
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:latest-mongodb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-mongodb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-mongodb-debian \
+ # latest-postgresql
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:latest-postgresql-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-postgresql-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-postgresql-debian \
+ # latest-mariadb
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:latest-mariadb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-mariadb-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-mariadb-debian \
+ # latest (all databases)
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:latest-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-debian \
+ # latest-slim
+ docker buildx imagetools create \
+ -t ghcr.io/$REPO_OWNER_LC/meshcentral:latest-slim-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-amd64-slim-debian \
+ ghcr.io/$REPO_OWNER_LC/meshcentral:${{ github.ref_name }}-arm64-slim-debian \
diff --git a/docker/01_nodoc b/docker/01_nodoc
new file mode 100644
index 00000000..da3bf156
--- /dev/null
+++ b/docker/01_nodoc
@@ -0,0 +1,18 @@
+# Exclude unneeded documentation files to save space
+
+# Don't install package docs
+path-exclude=/usr/share/doc/*
+path-include=/usr/share/doc/*/copyright
+
+# Don't install man pages
+path-exclude=/usr/share/man/*
+
+# Don't install localized man pages
+path-exclude=/usr/share/locale/*
+
+# Optional: exclude info pages
+path-exclude=/usr/share/info/*
+
+# Optional: exclude lintian and other package data
+path-exclude=/usr/share/lintian/*
+path-exclude=/usr/share/linda/*
diff --git a/docker/Dockerfile b/docker/Dockerfile
index 6c479e0f..547bdae7 100644
--- a/docker/Dockerfile
+++ b/docker/Dockerfile
@@ -49,8 +49,7 @@ RUN rm -rf /opt/meshcentral/meshcentral/docker /opt/meshcentral/meshcentral/node
FROM node:22-alpine3.22 AS dep-compiler
-RUN apk update && \
- echo -e "----------\nINSTALLING ALPINE PACKAGES...\n----------"; \
+RUN echo -e "----------\nINSTALLING ALPINE PACKAGES...\n----------"; \
apk add --no-cache --update \
bash gcc g++ jq make python3 tzdata
@@ -59,13 +58,15 @@ WORKDIR /opt/meshcentral/meshcentral
RUN jq '.dependencies += {"modern-syslog": "1.2.0", "telegram": "2.26.22"}' package.json > temp.json && mv temp.json package.json \
&& npm i --package-lock-only \
- && npm ci
+ && npm ci --omit=dev \
+ && npm cache clean --force
-### STAGE 3 RUNTIME
+### STAGE 3 BUILDING.
-FROM node:22-alpine3.22 AS runtime
+FROM node:22-alpine3.22 AS finalizer
+#FROM alpine:3.22 AS finalizer
-# # Copy prepared app from builder stage
+# copy files from previous layer
COPY --from=dep-compiler /opt/meshcentral/meshcentral /opt/meshcentral/meshcentral
# environment variables
@@ -122,12 +123,12 @@ ENV MARIADB_HOST="" \
MARIADB_PASS="" \
MARIADB_DATABASE=""
+RUN mkdir -p /opt/meshcentral/meshcentral
WORKDIR /opt/meshcentral
-RUN apk update && \
- echo -e "----------\nINSTALLING ALPINE PACKAGES...\n----------"; \
+RUN echo -e "----------\nINSTALLING ALPINE PACKAGES...\n----------"; \
apk add --no-cache --update \
- bash curl jq nodejs npm tzdata && \
+ bash curl jq tzdata && \
rm -rf /var/cache/* \
/tmp/* \
/usr/share/man/ \
@@ -189,25 +190,22 @@ RUN case "$INCLUDE_MARIADB_TOOLS" in \
exit 1;; \
esac
-# install dependencies from package.json
-RUN cd meshcentral && \
- npm cache clean --force && \
- rm -rf /root/ /tmp/
+# Remove left over files and cache
+RUN cd meshcentral \
+ && rm -rf /root /tmp/* /var/tmp/* /usr/lib/node_modules/npm/man /usr/lib/node_modules/npm/doc /usr/lib/node_modules/npm/html \
+ && npm cache clean --force
# Expose needed ports
EXPOSE 80 443
-# These volumes will be created by default even without any declaration, this allows default persistence in Docker/Podman.
+# These volumes will be created by default even without any declaration, this allows default persistence in Docker/Podman. Dummy-proofing.
VOLUME /opt/meshcentral/meshcentral-data
VOLUME /opt/meshcentral/meshcentral-files
VOLUME /opt/meshcentral/meshcentral-web
VOLUME /opt/meshcentral/meshcentral-backups
# Copy images from Git repo, place it before ending so recompilation can make good use of cache.
-COPY ./docker/entrypoint.sh /opt/meshcentral/entrypoint.sh
+COPY ./docker/entrypoint.sh /opt/meshcentral/entrypoint.sh
COPY ./docker/config.json.template /opt/meshcentral/config.json.template
-HEALTHCHECK --interval=30s --timeout=5s --start-period=5s --retries=3 \
- CMD curl -k --fail https://localhost:443/health.ashx || exit 1
-
-ENTRYPOINT ["bash", "/opt/meshcentral/entrypoint.sh"]
+ENTRYPOINT ["bash", "/opt/meshcentral/entrypoint.sh"]
\ No newline at end of file
diff --git a/docker/Dockerfile-debian b/docker/Dockerfile-debian
new file mode 100644
index 00000000..a397da6f
--- /dev/null
+++ b/docker/Dockerfile-debian
@@ -0,0 +1,238 @@
+### STAGE 1 BUILDING.
+FROM node:22-trixie-slim AS builder
+
+# Any value inside one of the disable ARGs will be accepted.
+ARG DISABLE_EXTRACT="yes"
+ARG DISABLE_MINIFY="yes"
+ARG DISABLE_TRANSLATE="yes"
+# NODE_OPTIONS="--max_old_space_size=4096"
+# If your process gets OOM killed, perhaps the above will help.
+
+RUN mkdir -p /opt/meshcentral/meshcentral
+WORKDIR /opt/meshcentral
+COPY ./ /opt/meshcentral/meshcentral/
+
+# Check the Docker build arguments and if they are empty do the task.
+RUN if [ -n "$DISABLE_EXTRACT" ] || [ -n "$DISABLE_MINIFY" ] || [ -n "$DISABLE_TRANSLATE" ]; then \
+ echo -e "----------\nPREPARING ENVIRONMENT...\n----------"; \
+ cd meshcentral && \
+ npm install html-minifier-terser@7.2.0 jsdom@26.0.0 esprima@4.0.1 && \
+ cd translate && \
+ case "$DISABLE_EXTRACT" in \
+ false|no|FALSE|NO) \
+ echo -e "----------\nSTARTING THE EXTRACTING PROCESS...\n----------"; \
+ node translate.js extractall;; \
+ *) \
+ echo "Setting EXTRACT as disabled.";; \
+ esac && \
+ case "$DISABLE_MINIFY" in \
+ false|no|FALSE|NO) \
+ echo -e "----------\nSTARTING THE MINIFYING PROCESS...\n----------"; \
+ node translate.js minifyall;; \
+ *) \
+ echo "Setting MINIFY as disabled.";; \
+ esac && \
+ case "$DISABLE_TRANSLATE" in \
+ false|no|FALSE|NO) \
+ echo -e "----------\nSTARTING THE TRANSLATING PROCESS...\n----------"; \
+ node translate.js translateall;; \
+ *) \
+ echo "Setting TRANSLATE as disabled.";; \
+ esac; \
+ npm uninstall html-minifier-terser jsdom esprima; \
+ fi
+# Possible more updated alternative? @minify-html/node@0.15.0 -> https://www.npmjs.com/package/@minify-html/node
+
+RUN rm -rf /opt/meshcentral/meshcentral/docker /opt/meshcentral/meshcentral/node_modules /opt/meshcentral/meshcentral/docs
+
+### STAGE 2 PRECOMPILE DEPS MODULE
+
+FROM node:22-trixie-slim AS dep-compiler
+
+ENV NODE_ENV="production"
+
+RUN apt-get update && \
+ echo -e "----------\nINSTALLING DEBIAN PACKAGES...\n----------"; \
+ apt-get install -y --no-install-recommends --no-install-suggests \
+ bash gcc g++ jq make python3 tzdata
+
+COPY --from=builder /opt/meshcentral/meshcentral /opt/meshcentral/meshcentral
+WORKDIR /opt/meshcentral/meshcentral
+
+RUN jq '.dependencies += {"modern-syslog": "1.2.0", "telegram": "2.26.22"}' package.json > temp.json && mv temp.json package.json \
+ && npm i --package-lock-only \
+ && npm ci --omit=dev \
+ && npm cache clean --force
+
+### STAGE 3 fun. building from source...
+
+FROM golang:trixie AS mongo-tools-compiler
+
+ARG INCLUDE_MONGODB_TOOLS="false"
+
+RUN apt-get update && \
+ apt-get install -y --no-install-recommends --no-install-suggests \
+ git lsb-release
+
+RUN case "$INCLUDE_MONGODB_TOOLS" in \
+ true|yes|TRUE|YES) \
+ git clone https://github.com/mongodb/mongo-tools /mongo-tools; \
+ cd /mongo-tools; \
+ ./make build -pkgs=mongodump,mongorestore;; \
+ false|no|FALSE|NO) \
+ echo "Not building MongoDB Tools from source, what a shame!"; \
+ mkdir -p /mongo-tools/bin;; \
+ *) \
+ echo "Invalid value for build argument INCLUDE_MONGODB_TOOLS, possible values: 'yes', 'true', 'no' or 'false'"; \
+ exit 1;; \
+ esac
+
+### STAGE 4 BUILDING.
+
+FROM node:22-trixie-slim AS finalizer
+
+# Copy files from previous layers
+COPY --from=dep-compiler /opt/meshcentral/meshcentral /opt/meshcentral/meshcentral
+COPY --from=mongo-tools-compiler /mongo-tools/bin/ /tmp/bin/
+
+# environment variables
+ENV NODE_ENV="production" \
+ CONFIG_FILE="/opt/meshcentral/meshcentral-data/config.json" \
+ DYNAMIC_CONFIG="false"
+
+# environment variables for the above defined MeshCentral Config.json. Can be done like that following: https://docs.docker.com/reference/dockerfile/#env
+ENV ALLOW_PLUGINS="false" \
+ ALLOW_NEW_ACCOUNTS="false" \
+ ALLOWED_ORIGIN="false" \
+ IFRAME="false" \
+ REGEN_SESSIONKEY="false" \
+ WEBRTC="false" \
+ LOCAL_SESSION_RECORDING="true" \
+ MINIFY="true" \
+ HOSTNAME="localhost" \
+ REVERSE_PROXY="" \
+ REVERSE_PROXY_TLS_PORT="443" \
+ TRUSTED_PROXY="" \
+ ARGS=""
+
+# Database
+# Multi-variable declaration to reduce layers.
+ENV USE_MONGODB="false" \
+ USE_POSTGRESQL="false" \
+ USE_MARIADB="false"
+
+# Preinstallation args one per line due to: https://docs.docker.com/reference/dockerfile/#arg
+ARG PREINSTALL_LIBS="false"
+ARG INCLUDE_MONGODB_TOOLS="false"
+ARG INCLUDE_POSTGRESQL_TOOLS="false"
+ARG INCLUDE_MARIADB_TOOLS="false"
+
+# MongoDB Variables
+# The following MONGO_URL variable overwrites most other mongoDb related varialbes.
+ENV MONGO_HOST="" \
+ MONGO_PORT="27017" \
+ MONGO_USERNAME="" \
+ MONGO_PASS="" \
+ MONGO_URL=""
+
+# PostgreSQL Variables
+ENV PSQL_HOST="" \
+ PSQL_PORT="5432" \
+ PSQL_USER="" \
+ PSQL_PASS="" \
+ PSQL_DATABASE=""
+
+# MariaDB/MySQL Variables.
+ENV MARIADB_HOST="" \
+ MARIADB_PORT="3306" \
+ MARIADB_USER="" \
+ MARIADB_PASS="" \
+ MARIADB_DATABASE=""
+
+WORKDIR /opt/meshcentral
+
+RUN apt-get update && \
+ echo -e "----------\nINSTALLING DEBIAN PACKAGES...\n----------"; \
+ apt-get install -y --no-install-recommends --no-install-suggests \
+ bash curl jq tzdata && \
+ rm -rf \
+ /var/cache/* \
+ /usr/share/man/ \
+ /usr/share/doc/ \
+ /var/log/* \
+ /var/spool/* \
+ /var/tmp/* \
+ /usr/lib/debug/ && \
+ npm install -g npm@latest
+
+RUN case "$PREINSTALL_LIBS" in \
+ true|yes|TRUE|YES) \
+ cd meshcentral && \
+ echo -e "----------\nPREINSTALLING LIBRARIES...\n----------"; \
+ npm install ssh2@1.16.0 nodemailer@6.10.1 image-size@2.0.2 wildleek@2.0.0 otplib@12.0.1 yub@0.11.1;; \
+ false|no|FALSE|NO) \
+ echo "Not pre-installing libraries.";; \
+ *) \
+ echo -e "Invalid value for build argument INCLUDE_POSTGRESQL_TOOLS, possible values: 'yes', 'true', 'no' or 'false'"; \
+ exit 1;; \
+ esac
+
+# NOTE: ALL MODULES MUST HAVE A VERSION NUMBER AND THE VERSION MUST MATCH THAT USED IN meshcentraljs mainStart()
+RUN case "$INCLUDE_MONGODB_TOOLS" in \
+ true|yes|TRUE|YES) \
+ mv /tmp/bin/* /usr/bin; \
+ cd meshcentral && \
+ echo -e "----------\nPREINSTALLING MONGODB LIBRARIES...\n----------"; \
+ npm install mongodb@4.17.2 @mongodb-js/saslprep@1.3.1;; \
+ false|no|FALSE|NO) \
+ echo "Not including MongoDB Tools.";; \
+ *) \
+ echo "Invalid value for build argument INCLUDE_MONGODB_TOOLS, possible values: 'yes', 'true', 'no' or 'false'"; \
+ exit 1;; \
+ esac
+
+RUN case "$INCLUDE_POSTGRESQL_TOOLS" in \
+ true|yes|TRUE|YES) \
+ apt-get install -y --no-install-recommends --no-install-suggests postgresql-client-17; \
+ cd meshcentral && \
+ echo -e "----------\nPREINSTALLING POSTGRESQL LIBRARIES...\n----------"; \
+ npm install pg@8.14.1;; \
+ false|no|FALSE|NO) \
+ echo "Not including PostgreSQL Tools.";; \
+ *) \
+ echo -e "Invalid value for build argument INCLUDE_POSTGRESQL_TOOLS, possible values: 'yes', 'true', 'no' or 'false'"; \
+ exit 1;; \
+ esac
+
+RUN case "$INCLUDE_MARIADB_TOOLS" in \
+ true|yes|TRUE|YES) \
+ apt-get install -y --no-install-recommends --no-install-suggests default-mysql-client mariadb-client; \
+ cd meshcentral && \
+ echo -e "----------\nPREINSTALLING MARIADB/MYSQL LIBRARIES...\n----------"; \
+ npm install mariadb@3.4.0 mysql2@3.11.4;; \
+ false|no|FALSE|NO) \
+ echo "Not including MariaDB/MySQL Tools.";; \
+ *) \
+ echo -e "Invalid value for build argument INCLUDE_MARIADB_TOOLS, possible values: 'yes', 'true', 'no' or 'false'"; \
+ exit 1;; \
+ esac
+
+# Remove left over files and cache
+RUN cd meshcentral \
+ && rm -rf /root /tmp/* /var/tmp/* /usr/lib/node_modules/npm/man /usr/lib/node_modules/npm/doc /usr/lib/node_modules/npm/html \
+ && npm cache clean --force
+
+# Expose needed ports
+EXPOSE 80 443
+
+# These volumes will be created by default even without any declaration, this allows default persistence in Docker/Podman. Dummy-proofing.
+VOLUME /opt/meshcentral/meshcentral-data
+VOLUME /opt/meshcentral/meshcentral-files
+VOLUME /opt/meshcentral/meshcentral-web
+VOLUME /opt/meshcentral/meshcentral-backups
+
+# Copy images from Git repo, place it before ending so recompilation can make good use of cache.
+COPY ./docker/entrypoint.sh /opt/meshcentral/entrypoint.sh
+COPY ./docker/config.json.template /opt/meshcentral/config.json.template
+
+ENTRYPOINT ["bash", "/opt/meshcentral/entrypoint.sh"]
\ No newline at end of file
diff --git a/docker/README.md b/docker/README.md
index 40e68450..a09a8630 100644
--- a/docker/README.md
+++ b/docker/README.md
@@ -27,6 +27,17 @@ So for another quick example: if you want to get a released version with a Mongo
So for another quick example: if you want a very slim image with the latest code and only a local database: `ghcr.io/ylianst/meshcentral:master-slim`
So as a last example: if you want to get a MariaDB/MySQL backend with MeshCentral version 1.1.53: `ghcr.io/ylianst/meshcentral:1.1.53-mysql`
+## Persistency
+
+The Docker image has since recently removed its default creation of volumes. It might not be what you want.
+If you still want to use volumes to make data persist across containers use Docker volumes (or Kubernetes PVCs).
+For examples of how to use these volumes, see the examples below. Most data resides inside:
+
+- /opt/meshcentral/meshcentral-backups
+- /opt/meshcentral/meshcentral-data (most important! Server configurations, certificates, etc... reside here.)
+- /opt/meshcentral/meshcentral-files
+- /opt/meshcentral/meshcentral-web (relevant if you use a custom theme, such as [Stylish-UI](https://github.com/melo-professional/Meshcentral-Stylish-UI))
+
## Environment Variables
Below is a breakdown of environment variables used in this setup.
diff --git a/docker/build-all-variants.sh b/docker/build-all-variants.sh
new file mode 100644
index 00000000..52c277b2
--- /dev/null
+++ b/docker/build-all-variants.sh
@@ -0,0 +1,15 @@
+#!/bin/bash
+
+if command -v docker > /dev/null; then
+ docker build ../. -f Dockerfile -t meshcentral:alpine-slim --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=false --build-arg=INCLUDE_POSTGRESQL_TOOLS=false --build-arg=INCLUDE_MARIADB_TOOLS=false
+ docker build ../. -f Dockerfile -t meshcentral:alpine-complete --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=true --build-arg=INCLUDE_POSTGRESQL_TOOLS=true --build-arg=INCLUDE_MARIADB_TOOLS=true
+ docker build ../. -f Dockerfile -t meshcentral:alpine-mongodb --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=true --build-arg=INCLUDE_POSTGRESQL_TOOLS=false --build-arg=INCLUDE_MARIADB_TOOLS=false
+ docker build ../. -f Dockerfile -t meshcentral:alpine-postgresql --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=false --build-arg=INCLUDE_POSTGRESQL_TOOLS=true --build-arg=INCLUDE_MARIADB_TOOLS=false
+ docker build ../. -f Dockerfile -t meshcentral:alpine-mysql --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=false --build-arg=INCLUDE_POSTGRESQL_TOOLS=false --build-arg=INCLUDE_MARIADB_TOOLS=true
+
+ docker build ../. -f Dockerfile-debian -t meshcentral:debian-slim --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=false --build-arg=INCLUDE_POSTGRESQL_TOOLS=false --build-arg=INCLUDE_MARIADB_TOOLS=false
+ docker build ../. -f Dockerfile-debian -t meshcentral:debian-complete --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=true --build-arg=INCLUDE_POSTGRESQL_TOOLS=true --build-arg=INCLUDE_MARIADB_TOOLS=true
+ docker build ../. -f Dockerfile-debian -t meshcentral:debian-mongodb --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=true --build-arg=INCLUDE_POSTGRESQL_TOOLS=false --build-arg=INCLUDE_MARIADB_TOOLS=false
+ docker build ../. -f Dockerfile-debian -t meshcentral:debian-postgresql --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=false --build-arg=INCLUDE_POSTGRESQL_TOOLS=true --build-arg=INCLUDE_MARIADB_TOOLS=false
+ docker build ../. -f Dockerfile-debian -t meshcentral:debian-mysql --build-arg=PREINSTALL_LIBS=true --build-arg=INCLUDE_MONGODB_TOOLS=false --build-arg=INCLUDE_POSTGRESQL_TOOLS=false --build-arg=INCLUDE_MARIADB_TOOLS=true
+fi
diff --git a/docker/entrypoint.sh b/docker/entrypoint.sh
index 04580c23..65f86b7c 100644
--- a/docker/entrypoint.sh
+++ b/docker/entrypoint.sh
@@ -14,12 +14,22 @@ trap graceful_shutdown SIGTERM
# Make the start more cleared when restarted.
echo "-------------------------------------------------------------"
date
-echo "Config file: $CONFIG_FILE"
+if [ -n "$CONFIG_FILE" ]; then
+ echo "Config file: $CONFIG_FILE"
+else
+ exit 1
+fi
# Failsafe to create a new config if the expected config is not there.
if [ -f "${CONFIG_FILE}" ]; then
echo "Pre-existing config found, not recreating..."
else
+ if [ ! -d $(dirname "$CONFIG_FILE") ]; then
+ echo "Creating meshcentral-data directory..."
+ mkdir -p /opt/meshcentral/meshcentral-data
+ fi
+
+ echo "Placing template into the relevant directory: $(dirname $CONFIG_FILE)"
cp /opt/meshcentral/config.json.template "${CONFIG_FILE}"
fi
@@ -260,7 +270,7 @@ if [[ ${DYNAMIC_CONFIG,,} =~ ^(true|yes)$ ]]; then
cat "$CONFIG_FILE"
else
- echo "Leaving config as-is."
+ echo "Leaving config as-is. Dynamic Configuration is off."
fi
# Actually start MeshCentral.
diff --git a/docker/tools/docker.build.sh b/docker/tools/docker.build.sh
deleted file mode 100644
index e025ea35..00000000
--- a/docker/tools/docker.build.sh
+++ /dev/null
@@ -1,132 +0,0 @@
-#!/bin/bash
-
-MSG="";
-PRUNE="false";
-OVERRIDE_TAGS="false";
-ENABLE_LOG="false";
-LOG_FILE="$(dirname -- "$( readlink -f -- "$0"; )")/build.log";
-
-function appendOutput()
-{
- if [ -z "${MSG}" ]; then echo -e "\n" > /dev/tty; fi
-
- ARGS=$@;
- LINE="${ARGS}\n";
- if [ -z "${ENABLE_LOG}" ] || [ "${ENABLE_LOG}" != "true" ]; then echo -e "${LINE}" > /dev/tty; else echo -e "${LINE}" 2>&1 | tee -a ${LOG_FILE}; fi
-
- MSG="${MSG}${LINE}";
-}
-
-function runDockerBuild()
-{
- if [ "${PRUNE}" == "true" ]; then
- if [ -z "${ENABLE_LOG}" ] || [ "${ENABLE_LOG}" != "true" ]; then docker system prune -a -f;
- else docker system prune -a -f | tee -a ${LOG_FILE}; fi
- fi
-
- STARTTS=$(date +%s);
- ARGS=$@;
-
- APP_VERSION=$(grep -o '"version":\s*"[^"]*"' ./package.json | cut -f4- -d\" | tr -d '"');
- BASE_TAGS="";
- if [ -z "${OVERRIDE_TAGS}" ] || [ "${OVERRIDE_TAGS}" != "true" ]; then
- BASE_TAGS="-t meshcentral:latest -t meshcentral:${APP_VERSION}";
- fi
-
- BUILD_CMD="docker build -f docker/Dockerfile --force-rm --no-cache ${ARGS} ${BASE_TAGS} .";
- appendOutput "Current build: ${BUILD_CMD}";
-
- if [ -z "${ENABLE_LOG}" ] || [ "${ENABLE_LOG}" != "true" ]; then ${BUILD_CMD}; else ${BUILD_CMD} | tee -a ${LOG_FILE}; fi
- if [ $? -ne 0 ]; then exit $?; fi
-
- IMAGEID=$(docker images --format "{{.ID}} {{.CreatedAt}}" | sort -rk 2 | awk 'NR==1{print $1}');
- appendOutput "\tImageId: ${IMAGEID}";
-
- ENDTS=$(date +%s);
- DIFSEC=$((${ENDTS}-${STARTTS}));
- if [ ${DIFSEC} -ge 60 ]; then
- TMPMIN=$((${DIFSEC}/60));
- TMPSEC=$((${DIFSEC}%60));
-
- if [ ${TMPMIN} -ge 60 ]; then
- TMPHOUR=$((${TMPMIN}/60));
- TMPMIN=$((${TMPMIN}%60));
-
- appendOutput "\tBuild time: ${TMPHOUR} hr ${TMPMIN} min ${TMPSEC} sec";
- else appendOutput "\tBuild time: ${TMPMIN} min ${TMPSEC} sec"; fi
- else appendOutput "\tBuild time: ${DIFSEC} sec"; fi
-
- IMG_SIZE=$(docker image inspect ${IMAGEID} | grep -o '"Size":\s*[^,]*' | cut -f2- -d ':' | tr -d ' ');
- expr $IMG_SIZE + 0 > /dev/null;
- appendOutput "\tImage size: ${IMG_SIZE} ($((${IMG_SIZE}/1024/1024))M)\n";
-
- return 0;
-}
-
-parent_path=$(dirname -- $(dirname -- "$( readlink -f -- "$0"; )"));
-if [ "${parent_path}" != "$(pwd -P)" ]; then
- echo -e "change working directory to: ${parent_path}" > /dev/tty;
- cd "${parent_path}";
-fi
-
-if ! [ -z $1 ]; then
- for arg in "$@"
- do
- case "${arg}" in
- --prune)
- PRUNE="true";
- shift 1;
- ;;
- --log)
- ENABLE_LOG="true";
- shift 1;
- ;;
- --no-tags)
- OVERRIDE_TAGS="true";
- shift 1;
- ;;
- --help)
- __usage="\n
- Usage: ./$(basename ${0}) [OPTIONS] [BUILD ARGUMENTS]\n
- \n
- Options:\n
- \t--log \t\twrite output to build.log file\n
- \t--no-tags \tdo not use default tags (meshcentral:latest and meshcentral:%VERSION%)\n
- \t--prune \tWARNING: This will remove:\n
- \t\t\t - all stopped docker containers\n
- \t\t\t - all docker networks not used by at least one container\n
- \t\t\t - all docker images without at least one container associated to them\n
- \t\t\t - all docker build cache\n
- \n
- Build arguments: \tAll build arguments are forwarded to the docker build command, so you can use any option accepted by 'docker build'\n
- \t\t\t(https://docs.docker.com/engine/reference/commandline/build/#options)\n\n
- \t--build-arg INCLUDE_MONGODBTOOLS=yes \tIncludes mongodb-tools (mongodump, ...) in the image\n
- \t--build-arg DISABLE_MINIFY=yes \t\tDisables minification of files\n
- \t--build-arg DISABLE_TRANSLATE=yes \tDisables translation of files\n
- ";
- echo -e $__usage;
- exit 0;
- ;;
- *)
- break;
- ;;
- esac
- done
-fi
-
-MAINARGS=$@;
-
-#runDockerBuild --build-arg DISABLE_MINIFY=yes --build-arg DISABLE_TRANSLATE=yes ${MAINARGS};
-#runDockerBuild --build-arg DISABLE_TRANSLATE=yes ${MAINARGS};
-#runDockerBuild --build-arg DISABLE_MINIFY=yes ${MAINARGS};
-runDockerBuild ${MAINARGS};
-
-#runDockerBuild --build-arg INCLUDE_MONGODBTOOLS=yes --build-arg DISABLE_MINIFY=yes --build-arg DISABLE_TRANSLATE=yes ${MAINARGS};
-#runDockerBuild --build-arg INCLUDE_MONGODBTOOLS=yes --build-arg DISABLE_TRANSLATE=yes ${MAINARGS};
-#runDockerBuild --build-arg INCLUDE_MONGODBTOOLS=yes --build-arg DISABLE_MINIFY=yes ${MAINARGS};
-#runDockerBuild --build-arg INCLUDE_MONGODBTOOLS=yes ${MAINARGS};
-
-echo "";
-if [ -z "${ENABLE_LOG}" ] || [ "${ENABLE_LOG}" != "true" ]; then echo -e "${MSG}"; else echo -e "${MSG}" 2>&1 | tee -a ${LOG_FILE}; fi
-
-exit 0;