diff --git a/anki-syncserver/Dockerfile b/anki-syncserver/Dockerfile new file mode 100644 index 0000000..0f5554c --- /dev/null +++ b/anki-syncserver/Dockerfile @@ -0,0 +1,40 @@ +FROM rust:1.85.0-alpine3.20 AS builder + +ARG ANKI_VERSION + +RUN apk update && apk add --no-cache build-base protobuf && rm -rf /var/cache/apk/* + +RUN cargo install --git https://github.com/ankitects/anki.git \ +--tag ${ANKI_VERSION} \ +--root /anki-server \ +--locked \ +anki-sync-server + +FROM alpine:3.21.0 + +# Default PUID and PGID values (can be overridden at runtime). Use these to +# ensure the files on the volume have the permissions you need. +ENV PUID=1000 +ENV PGID=1000 + +COPY --from=builder /anki-server/bin/anki-sync-server /usr/local/bin/anki-sync-server + +RUN apk update && apk add --no-cache bash su-exec && rm -rf /var/cache/apk/* + + +EXPOSE 8080 + +COPY entrypoint.sh /entrypoint.sh +RUN chmod +x /entrypoint.sh + +ENTRYPOINT ["/entrypoint.sh"] +CMD ["anki-sync-server"] + +# This health check will work for Anki versions 24.08.x and newer. +# For older versions, it may incorrectly report an unhealthy status, which should not be the case. +HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \ + CMD wget -qO- http://127.0.0.1:8080/health || exit 1 + +VOLUME /anki_data + +LABEL maintainer="Jean Khawand " diff --git a/anki-syncserver/docker-compose.yml b/anki-syncserver/docker-compose.yml new file mode 100644 index 0000000..2bd281a --- /dev/null +++ b/anki-syncserver/docker-compose.yml @@ -0,0 +1,31 @@ +networks: + default: + name: traefik_default + external: true + +services: + anki-syncserver: + container_name: anki-syncserver + build: + dockerfile: Dockerfile + args: + - ANKI_VERSION=25.09 + env_file: live.env + ports: + - "8080:8080" + environment: + - SYNC_USER1=${USER_NAME}:${USER_PASSWORD} + volumes: + - ./data:/anki-sync-server-data + labels: + # Watchtower + - "com.centurylinklabs.watchtower.enable=true" + # Routes + - "traefik.enable=true" + - "traefik.http.routers.anki.entrypoints=websecure" + - "traefik.http.routers.anki.rule=Host(`anki.${DOMAIN}`)" + - "traefik.http.routers.anki.tls=true" + - "traefik.http.routers.anki.tls.certresolver=myresolver" + - "traefik.http.services.anki.loadbalancer.server.port=8080" + networks: + - default diff --git a/anki-syncserver/entrypoint.sh b/anki-syncserver/entrypoint.sh new file mode 100644 index 0000000..072ae15 --- /dev/null +++ b/anki-syncserver/entrypoint.sh @@ -0,0 +1,30 @@ +#!/bin/sh +set -o errexit +set -o nounset +set -o pipefail + +# Default PUID and PGID if not provided +export PUID=${PUID:-1000} +export PGID=${PGID:-1000} + +# These values are fixed and cannot be overwritten from the outside for +# convenience and safety reasons +export SYNC_PORT=8080 +export SYNC_BASE=/anki_data + +# Check if group exists, create if not +if ! getent group anki-group > /dev/null 2>&1; then + addgroup -g "$PGID" anki-group +fi + +# Check if user exists, create if not +if ! id -u anki > /dev/null 2>&1; then + adduser -D -H -u "$PUID" -G anki-group anki +fi + +# Fix ownership of mounted volumes +mkdir -p /anki_data +chown anki:anki-group /anki_data + +# Run the provided command as the `anki` user +exec su-exec anki "$@" diff --git a/anki-syncserver/live.env.tpl b/anki-syncserver/live.env.tpl new file mode 100644 index 0000000..a77a49d --- /dev/null +++ b/anki-syncserver/live.env.tpl @@ -0,0 +1,7 @@ +# Anki Syncserver +ANKI_VERSION=25.09 +USER_NAME=admin +USER_PASSWORD=password + +# Traefik +DOMAIN=sporada.eu