Files
bentopdf/docs/uk/self-hosting/docker.md
T

37 KiB
Raw Blame History

Розгортання з Docker / Podman

Найпростіший спосіб самостійно розгорнути BentoPDF у робочому середовищі.

Important

Обов'язкові заголовки для конвертації офісних файлів

Інструменти на основі LibreOffice (конвертація Word, Excel, PowerPoint) потребують таких HTTP-заголовків для підтримки SharedArrayBuffer:

  • Cross-Origin-Opener-Policy: same-origin
  • Cross-Origin-Embedder-Policy: require-corp

Сторінка також має віддаватися з безпечного контексту. http://localhost підходить для локального тестування, але http://192.168.x.x та інші LAN-адреси зазвичай не відповідають вимогам, тому конвертація Office через звичайний HTTP не працюватиме, навіть якщо заголовки присутні.

Офіційні образи контейнерів містять ці заголовки. Якщо ви використовуєте зворотний проксі (Traefik, Caddy тощо), переконайтеся, що ці заголовки зберігаються або додаються, і використовуйте HTTPS для доступу не з loopback.

Tip

Користувачам Podman: усі команди docker працюють з Podman, якщо замінити docker на podman, а docker-compose на podman-compose.

Швидкий старт

Tip

BentoPDF постачається у двох збірках:

  • Self-Hosted build: ghcr.io/alam00000/bentopdf-simple:latest. Усі PDF-інструменти, без маркетингових елементів (без головного екрана, FAQ, відгуків і футера). Використовуйте для внутрішніх розгортань у командах і організаціях. Це не урізана "lite"-версія.
  • Commercial build: ghcr.io/alam00000/bentopdf:latest. Повний маркетинговий сайт, який використовує сам bentopdf.com і власники комерційної ліцензії для публічних розгортань.

Якщо вагаєтеся, беріть Self-Hosted build.

# Docker
docker run -d \
  --name bentopdf \
  -p 3000:8080 \
  --restart unless-stopped \
  ghcr.io/alam00000/bentopdf-simple:latest

# Podman
podman run -d \
  --name bentopdf \
  -p 3000:8080 \
  ghcr.io/alam00000/bentopdf-simple:latest

Docker Compose / Podman Compose

Створіть docker-compose.yml:

services:
  bentopdf:
    image: ghcr.io/alam00000/bentopdf-simple:latest
    container_name: bentopdf
    ports:
      - '3000:8080'
    restart: unless-stopped
    healthcheck:
      test: ['CMD', 'wget', '--spider', '-q', 'http://localhost:8080']
      interval: 30s
      timeout: 10s
      retries: 3

Запустіть:

# Docker Compose
docker compose up -d

# Podman Compose
podman-compose up -d

Збірка власного образу

# Dockerfile
FROM node:20-alpine AS builder
WORKDIR /app
ENV HUSKY=0
COPY package*.json ./
COPY vendor ./vendor
RUN npm ci
COPY . .
RUN npm run build

FROM nginxinc/nginx-unprivileged:alpine
COPY --from=builder /app/dist /usr/share/nginx/html
COPY --from=builder /app/security-headers.conf /etc/nginx/security-headers.conf
COPY --from=builder /app/security-headers-docs.conf /etc/nginx/security-headers-docs.conf
COPY nginx.conf /etc/nginx/nginx.conf
RUN mkdir -p /etc/nginx/tmp
EXPOSE 8080
CMD ["nginx", "-g", "daemon off;"]

Зберіть і запустіть:

docker build -t bentopdf:custom .
docker run -d -p 3000:8080 bentopdf:custom

Змінні середовища

Змінна Опис Типове значення
SIMPLE_MODE Зібрати варіант Self-Hosted (ховає маркетингові елементи bentopdf.com: головний екран, FAQ, відгуки, футер). Усі PDF-інструменти залишаються. false
BASE_URL Розгортання в підкаталозі /
VITE_WASM_PYMUPDF_URL URL модуля PyMuPDF WASM https://cdn.jsdelivr.net/npm/@bentopdf/[email protected]/
VITE_WASM_GS_URL URL модуля Ghostscript WASM https://cdn.jsdelivr.net/npm/@bentopdf/[email protected]/assets/
VITE_WASM_CPDF_URL URL модуля CoherentPDF WASM https://cdn.jsdelivr.net/npm/[email protected]/dist/
VITE_TESSERACT_WORKER_URL URL скрипта OCR worker (порожньо; CDN Tesseract.js за замовчуванням)
VITE_TESSERACT_CORE_URL Каталог основного runtime OCR (порожньо; CDN Tesseract.js за замовчуванням)
VITE_TESSERACT_LANG_URL Каталог traineddata OCR (порожньо; CDN Tesseract.js за замовчуванням)
VITE_TESSERACT_AVAILABLE_LANGUAGES Мови OCR через кому, що відображаються в інтерфейсі (порожньо; показати повний каталог)
VITE_OCR_FONT_BASE_URL Каталог шрифтів текстового шару OCR (порожньо; використовувати віддалені URL шрифтів Noto)
VITE_DEFAULT_LANGUAGE Типова мова інтерфейсу en
VITE_BRAND_NAME Власна назва бренду BentoPDF
VITE_BRAND_LOGO Шлях до логотипа відносно public/ images/favicon-no-bg.svg
VITE_FOOTER_TEXT Власний текст футера/авторських прав © 2026 BentoPDF. All rights reserved.
DISABLE_TOOLS ID інструментів через кому, які потрібно сховати (порожньо; усі інструменти ввімкнено)
DISABLE_GITHUB_STARS Пропустити отримання кількості зірок GitHub під час завантаження сторінки та прибрати api.github.com із CSP. Збірки Simple Mode завжди це пропускають. false
SITE_URL Публічний URL, що записується в canonical, hreflang і посилання sitemap. Залиште типовим, якщо не хочете, щоб пошукові системи сприймали ваше розгортання як окремий сайт. https://www.bentopdf.com
ALLOW_INDEXING Із власним SITE_URL кожну сторінку позначено noindex, щоб ваша копія не конкурувала з bentopdf.com у пошуку. Задайте true, щоб дозволити пошуковим системам її індексувати. false
COMPRESSION_MODE Попередньо стиснені копії поруч із кожним файлом: o немає, g .gz (їх віддає nginx образу), b .br, all обидві. Nginx образу не вміє віддавати .br. o

URL модулів WASM попередньо налаштовано з типовими значеннями CDN, тому всі розширені функції працюють одразу. Перевизначте їх для ізольованих (air-gapped) або самостійно розгорнутих середовищ.

Пошукові системи

За замовчуванням кожна сторінка вказує пошуковим системам на bentopdf.com як на оригінал, тож ваше розгортання не з'являється як дублікат. Для приватного чи внутрішнього екземпляра нічого змінювати не потрібно.

  • Повністю сховати екземпляр із результатів пошуку: запустіть контейнер із -e ROBOTS_NOINDEX=true. Для цього потрібен лише перезапуск, без перезбирання.
  • Зробити екземпляр окремим сайтом у результатах пошуку: зберіть із --build-arg SITE_URL=https://your-domain.example --build-arg ALLOW_INDEXING=true. Без ALLOW_INDEXING=true власний SITE_URL позначає кожну сторінку як noindex.

Content-Security-Policy

Образ nginx постачається із заголовком Content-Security-Policy у режимі примусового застосування. Директиви CSP script-src, connect-src і font-src генеруються під час збірки зі змінних URL VITE_* вище: усі хости, які ви передаєте через --build-arg, автоматично додаються до політики.

Отже:

  • Якщо ви перевизначаєте VITE_CORS_PROXY_URL або VITE_WASM_*_URL під час збірки, CSP автоматично дозволяє ці origin, додаткове налаштування не потрібне.
  • Для URL на cdn.jsdelivr.net script-src дозволяє лише точну версійну папку пакета, наприклад https://cdn.jsdelivr.net/npm/@bentopdf/[email protected]/, а не весь CDN. jsDelivr віддає будь-який публічний пакет npm або репозиторій GitHub, тож дозвіл усього хоста дав би змогу запускати будь-який із них на вашому екземплярі. URL на будь-яких інших хостах дозволяються за origin.
  • Якщо ви налаштовуєте власні URL WASM під час роботи через сторінку «Додаткові налаштування» у застосунку, ці origin не потрапляють до CSP, і браузер блокуватиме запити до них. Це також стосується іншої версії того самого пакета на cdn.jsdelivr.net, бо дозволено лише версію, задану під час збірки. Налаштування під час роботи призначене для експериментів; для постійних власних URL задайте відповідний build arg VITE_*.
  • Ізольовані розгортання, що перевизначають усі три значення VITE_WASM_*_URL, також позбуваються цих папок пакетів cdn.jsdelivr.net у CSP (кожне типове значення замінюється, а не доповнюється). Типові значення Tesseract OCR на cdn.jsdelivr.net залишаються в політиці, доки ви також не задасте три значення VITE_TESSERACT_*. Так само задання VITE_CORS_PROXY_URL замінює публічне типове значення bentopdf-cors-proxy.bentopdf.workers.dev.

CSP містить 'unsafe-eval' у script-src, тому що runtime LibreOffice WASM (використовується інструментами конвертації Word/Excel/PowerPoint) і бібліотека зображень wasm-vips (використовується для PDF у TIFF) компілюють внутрішній диспетчерський код через new Function(). Його видалення зламало б ці інструменти. Якщо ви збираєте в SIMPLE_MODE (без LibreOffice) і не потребуєте PDF у TIFF, можна вручну відредагувати згенерований security-headers.conf, прибравши 'unsafe-eval' для суворішої політики.

Для OCR залиште змінні VITE_TESSERACT_* порожніми, щоб використовувати типові онлайн-ресурси, або задайте всі три разом для самостійного/офлайн OCR. Часткові перевизначення OCR відхиляються, бо worker, основний runtime і каталог traineddata мають збігатися. Для повністю офлайн-виводу пошукового PDF також задайте VITE_OCR_FONT_BASE_URL, щоб шрифти текстового шару OCR завантажувалися з вашого внутрішнього сервера, а не з публічних URL шрифтів Noto.

VITE_DEFAULT_LANGUAGE задає мову інтерфейсу для нових відвідувачів. Підтримувані значення: en, ar, be, fr, de, es, zh, zh-TW, vi, tr, id, it, pt, nl, da. Користувачі й далі можуть змінювати мову: це змінює лише типове значення.

Приклад:

# Build with French as the default language
docker build --build-arg VITE_DEFAULT_LANGUAGE=fr -t bentopdf .
docker run -d -p 3000:8080 bentopdf

Власний брендинг

Замініть типовий логотип BentoPDF, назву та текст футера на свої. Помістіть файл логотипа в папку public/ (або використайте наявне зображення), а потім передайте змінні брендингу під час збірки:

docker build \
  --build-arg VITE_BRAND_NAME="AcmePDF" \
  --build-arg VITE_BRAND_LOGO="images/acme-logo.svg" \
  --build-arg VITE_FOOTER_TEXT="© 2026 Acme Corp. Internal use only." \
  -t acmepdf .

Брендинг працює і в повному режимі, і в Simple Mode, і його можна поєднувати з усіма іншими параметрами збірки.

Вимкнення окремих інструментів

Ховайте інструменти з інтерфейсу з міркувань відповідності вимогам або безпеки. Вимкнені інструменти прибираються з головної сторінки, результатів пошуку, клавіатурних скорочень і конструктора робочих процесів. Прямий доступ за URL показує сторінку "інструмент недоступний".

ID інструмента це URL сторінки без .html. Наприклад, якщо інструмент розташований за адресою bentopdf.com/edit-pdf.html, ID це edit-pdf.

Як знайти ID інструментів

Найпростіше: відкрийте будь-який інструмент у BentoPDF і подивіться на URL. Остання частина шляху (без .html) це ID інструмента.

Повний список ID інструментів

Редагування й анотації: edit-pdf, bookmark, table-of-contents, page-numbers, add-page-labels, bates-numbering, add-watermark, header-footer, invert-colors, scanner-effect, adjust-colors, background-color, text-color, sign-pdf, add-stamps, remove-annotations, crop-pdf, form-filler, form-creator, remove-blank-pages

Конвертація в PDF: image-to-pdf, jpg-to-pdf, png-to-pdf, webp-to-pdf, svg-to-pdf, bmp-to-pdf, heic-to-pdf, tiff-to-pdf, txt-to-pdf, markdown-to-pdf, json-to-pdf, csv-to-pdf, rtf-to-pdf, odt-to-pdf, word-to-pdf, excel-to-pdf, powerpoint-to-pdf, xps-to-pdf, mobi-to-pdf, epub-to-pdf, fb2-to-pdf, cbz-to-pdf, wpd-to-pdf, wps-to-pdf, xml-to-pdf, pages-to-pdf, odg-to-pdf, ods-to-pdf, odp-to-pdf, pub-to-pdf, vsd-to-pdf, psd-to-pdf, email-to-pdf

Конвертація з PDF: pdf-to-jpg, pdf-to-png, pdf-to-webp, pdf-to-bmp, pdf-to-tiff, pdf-to-cbz, pdf-to-svg, pdf-to-csv, pdf-to-excel, pdf-to-greyscale, pdf-to-json, pdf-to-docx, extract-images, pdf-to-markdown, prepare-pdf-for-ai, pdf-to-text

Організація й керування: ocr-pdf, merge-pdf, alternate-merge, organize-pdf, add-attachments, extract-attachments, edit-attachments, pdf-multi-tool, pdf-layers, extract-tables, split-pdf, divide-pages, extract-pages, delete-pages, add-blank-page, reverse-pages, rotate-pdf, rotate-custom, n-up-pdf, pdf-booklet, combine-single-page, view-metadata, edit-metadata, pdf-to-zip, compare-pdfs, posterize-pdf, page-dimensions

Оптимізація й відновлення: compress-pdf, pdf-to-pdfa, fix-page-size, linearize-pdf, remove-restrictions, repair-pdf, rasterize-pdf, deskew-pdf, font-to-outline

Безпека: encrypt-pdf, sanitize-pdf, decrypt-pdf, flatten-pdf, remove-metadata, change-permissions, digital-sign-pdf, validate-signature-pdf, timestamp-pdf

Варіант 1: під час збірки (build arg Docker)

docker build \
  --build-arg DISABLE_TOOLS="edit-pdf,sign-pdf,encrypt-pdf" \
  -t bentopdf .

Це вшиває список вимкнених інструментів у JavaScript-бандл. Для зміни потрібне перезбирання.

Варіант 2: під час роботи (config.json)

Змонтуйте файл config.json у каталог, що віддається, перезбирання не потрібне:

{
  "disabledTools": ["edit-pdf", "sign-pdf", "encrypt-pdf"]
}
docker run -d \
  -p 3000:8080 \
  -v ./config.json:/usr/share/nginx/html/config.json:ro \
  ghcr.io/alam00000/bentopdf-simple:latest

Або з Docker Compose:

services:
  bentopdf:
    image: ghcr.io/alam00000/bentopdf-simple:latest
    ports:
      - '3000:8080'
    volumes:
      - ./config.json:/usr/share/nginx/html/config.json:ro

Обидва способи можна поєднувати: списки об'єднуються. Якщо інструмент є в будь-якому з них, його вимкнено.

Вимкнення функцій редактора

Ви також можете вимкнути окремі функції всередині PDF-редактора (наприклад, редагування (redaction), анотації, форми), не вимикаючи весь інструмент редактора. Додайте editorDisabledCategories до config.json:

{
  "editorDisabledCategories": ["redaction", "annotation-stamp"]
}
Повний список категорій редактора

Масштаб: zoom, zoom-in, zoom-out, zoom-fit-page, zoom-fit-width, zoom-marquee, zoom-level

Анотації: annotation, annotation-markup, annotation-highlight, annotation-underline, annotation-strikeout, annotation-squiggly, annotation-ink, annotation-text, annotation-stamp

Фігури: annotation-shape, annotation-rectangle, annotation-circle, annotation-line, annotation-arrow, annotation-polygon, annotation-polyline

Вимірювання: annotation-measurement, mode-measure, annotation-distance, annotation-perimeter, annotation-area

Форми: form, form-textfield, form-checkbox, form-radio, form-select, form-listbox, form-fill-mode

Приховування даних: redaction, redaction-area, redaction-text, redaction-apply, redaction-clear

Документ: document, document-open, document-close, document-print, document-capture, document-export, document-fullscreen, document-protect

Сторінка: page, spread, rotate, scroll, navigation

Панель: panel, panel-sidebar, panel-search, panel-comment

Інструменти: tools, pan, pointer, capture, organize

Виділення: selection, selection-copy

Історія: history, history-undo, history-redo

Категорії ієрархічні: вимкнення батьківської (наприклад, annotation) вимикає всі її дочірні.

Вимкнення лічильника зірок GitHub

Навігаційна панель показує актуальну кількість зірок GitHub, яку отримують з api.github.com під час завантаження сторінки. Це єдиний зовнішній запит, що не обслуговує жодну функцію PDF. Вимкніть його під час збірки, щоб прибрати код отримання з бандла та api.github.com із Content-Security-Policy:

docker build --build-arg DISABLE_GITHUB_STARS=true -t bentopdf .

Збірки Simple Mode (bentopdf-simple) завжди пропускають лічильник зірок: цей прапорець потрібен лише для Commercial build або власних повних збірок.

Власні URL WASM (ізольовані / самостійно розгорнуті середовища)

Important

URL WASM вшиваються в JavaScript під час збірки. Файли WASM завантажує браузер користувача під час роботи: Docker не завантажує їх під час збірки. Для ізольованих мереж потрібно розмістити файли WASM на внутрішньому сервері, доступному для браузерів.

Повний процес для ізольованого середовища:

# 1. On a machine WITH internet — download WASM packages
bash scripts/prepare-airgap.sh --list-ocr-languages
bash scripts/prepare-airgap.sh --search-ocr-language german

# 2. Download WASM/OCR packages
npm pack @bentopdf/[email protected]
npm pack @bentopdf/gs-wasm
npm pack coherentpdf
npm pack [email protected]
npm pack [email protected]
mkdir -p tesseract-langdata
curl -fsSL https://cdn.jsdelivr.net/npm/@tesseract.js-data/eng/4.0.0_best_int/eng.traineddata.gz -o tesseract-langdata/eng.traineddata.gz
mkdir -p ocr-fonts
curl -fsSL https://raw.githack.com/googlefonts/noto-fonts/main/hinted/ttf/NotoSans/NotoSans-Regular.ttf -o ocr-fonts/NotoSans-Regular.ttf

# 3. Build the image with your internal server URLs
docker build \
  --build-arg VITE_WASM_PYMUPDF_URL=https://internal-server.example.com/wasm/pymupdf/ \
  --build-arg VITE_WASM_GS_URL=https://internal-server.example.com/wasm/gs/ \
  --build-arg VITE_WASM_CPDF_URL=https://internal-server.example.com/wasm/cpdf/ \
  --build-arg VITE_TESSERACT_WORKER_URL=https://internal-server.example.com/wasm/ocr/worker.min.js \
  --build-arg VITE_TESSERACT_CORE_URL=https://internal-server.example.com/wasm/ocr/core \
  --build-arg VITE_TESSERACT_LANG_URL=https://internal-server.example.com/wasm/ocr/lang-data \
  --build-arg VITE_TESSERACT_AVAILABLE_LANGUAGES=eng,deu \
  --build-arg VITE_OCR_FONT_BASE_URL=https://internal-server.example.com/wasm/ocr/fonts \
  -t bentopdf .

# 4. Export the image
docker save bentopdf -o bentopdf.tar

# 5. Transfer bentopdf.tar + the .tgz packages + tesseract-langdata/ + ocr-fonts/ into the air-gapped network

# 6. Inside the air-gapped network — load and run
docker load -i bentopdf.tar

# Extract WASM packages to your internal web server
mkdir -p /var/www/wasm/pymupdf /var/www/wasm/gs /var/www/wasm/cpdf /var/www/wasm/ocr/core /var/www/wasm/ocr/lang-data /var/www/wasm/ocr/fonts
tar xzf bentopdf-pymupdf-wasm-0.11.14.tgz -C /var/www/wasm/pymupdf --strip-components=1
tar xzf bentopdf-gs-wasm-*.tgz -C /var/www/wasm/gs --strip-components=1
tar xzf coherentpdf-*.tgz -C /var/www/wasm/cpdf --strip-components=1
TEMP_TESS=$(mktemp -d)
tar xzf tesseract.js-7.0.0.tgz -C "$TEMP_TESS"
cp "$TEMP_TESS/package/dist/worker.min.js" /var/www/wasm/ocr/worker.min.js
rm -rf "$TEMP_TESS"
tar xzf tesseract.js-core-7.0.0.tgz -C /var/www/wasm/ocr/core --strip-components=1
cp ./tesseract-langdata/*.traineddata.gz /var/www/wasm/ocr/lang-data/
cp ./ocr-fonts/* /var/www/wasm/ocr/fonts/

# Run BentoPDF
docker run -d -p 3000:8080 --restart unless-stopped bentopdf

Для --ocr-languages використовуйте коди, які виводить bash scripts/prepare-airgap.sh --list-ocr-languages, або шукайте за назвою через bash scripts/prepare-airgap.sh --search-ocr-language <term>. Коли ви збираєте з обмеженим набором мов OCR, передайте ті самі коди в VITE_TESSERACT_AVAILABLE_LANGUAGES, щоб застосунок показував лише вбудовані мови. Для повного офлайн-виводу OCR також розмістіть вбудований каталог ocr-fonts/ і вкажіть на нього VITE_OCR_FONT_BASE_URL.

Задайте змінній порожній рядок, щоб вимкнути відповідний модуль (користувачі мають налаштувати його вручну через «Додаткові налаштування»).

Власний порт

За замовчуванням BentoPDF слухає порт 8080 усередині контейнера. Щоб його змінити, задайте змінну середовища PORT під час запуску:

docker run -p 3000:9090 -e PORT=9090 ghcr.io/alam00000/bentopdf-simple:latest
Змінна Опис Типове значення
PORT Порт, який слухає Nginx у контейнері 8080

Це працює і зі стандартним, і з nonroot Dockerfile.

Власний ID користувача (PUID/PGID)

Для середовищ, які вимагають запуску від конкретного користувача без прав root (NAS-пристрої, Kubernetes із контекстами безпеки, організаційні політики), BentoPDF надає окремий Dockerfile з підтримкою PUID/PGID у стилі LSIO.

Збірка і запуск

# Build the non-root image
docker build -f Dockerfile.nonroot -t bentopdf-nonroot .

# Run with custom UID/GID
docker run -d \
  --name bentopdf \
  -p 3000:8080 \
  -e PUID=1000 \
  -e PGID=1000 \
  --restart unless-stopped \
  bentopdf-nonroot

Змінні середовища

Змінна Опис Типове значення
PUID ID користувача для запуску 1000
PGID ID групи для запуску 1000
PORT Порт, який слухає Nginx 8080
DISABLE_IPV6 Вимкнути слухача IPv6 false

Docker Compose

services:
  bentopdf:
    build:
      context: .
      dockerfile: Dockerfile.nonroot
    container_name: bentopdf
    ports:
      - '3000:8080'
    environment:
      - PUID=1000
      - PGID=1000
    restart: unless-stopped

Як це працює

Контейнер запускається від root, створює користувача із заданими PUID/PGID, налаштовує власника для всіх каталогів із правом запису, а потім скидає привілеї за допомогою su-exec. Процес nginx повністю працює від указаного вами користувача.

Note

Стандартний Dockerfile використовує nginx-unprivileged (UID 101) і рекомендований для більшості розгортань. Використовуйте Dockerfile.nonroot лише тоді, коли потрібен конкретний UID/GID.

Warning

PUID/PGID не можуть бути 0 (root). Точка входу перевіряє вхідні дані та завершиться з помилкою для недійсних значень.

З Traefik (зворотний проксі)

services:
  traefik:
    image: traefik:v2.10
    command:
      - '--providers.docker=true'
      - '--entrypoints.web.address=:80'
      - '--entrypoints.websecure.address=:443'
      - '[email protected]'
      - '--certificatesresolvers.letsencrypt.acme.storage=/letsencrypt/acme.json'
      - '--certificatesresolvers.letsencrypt.acme.httpchallenge.entrypoint=web'
    ports:
      - '80:80'
      - '443:443'
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock:ro
      - ./letsencrypt:/letsencrypt

  bentopdf:
    image: ghcr.io/alam00000/bentopdf-simple:latest
    labels:
      - 'traefik.enable=true'
      - 'traefik.http.routers.bentopdf.rule=Host(`pdf.example.com`)'
      - 'traefik.http.routers.bentopdf.entrypoints=websecure'
      - 'traefik.http.routers.bentopdf.tls.certresolver=letsencrypt'
      - 'traefik.http.services.bentopdf.loadbalancer.server.port=8080'
      # Required headers for SharedArrayBuffer (LibreOffice WASM)
      - 'traefik.http.routers.bentopdf.middlewares=bentopdf-headers'
      - 'traefik.http.middlewares.bentopdf-headers.headers.customresponseheaders.Cross-Origin-Opener-Policy=same-origin'
      - 'traefik.http.middlewares.bentopdf-headers.headers.customresponseheaders.Cross-Origin-Embedder-Policy=require-corp'
    restart: unless-stopped

З Caddy (зворотний проксі)

services:
  caddy:
    image: caddy:2
    ports:
      - '80:80'
      - '443:443'
    volumes:
      - ./Caddyfile:/etc/caddy/Caddyfile
      - caddy_data:/data

  bentopdf:
    image: ghcr.io/alam00000/bentopdf-simple:latest
    restart: unless-stopped

volumes:
  caddy_data:

Caddyfile:

pdf.example.com {
    reverse_proxy bentopdf:8080
    header Cross-Origin-Opener-Policy "same-origin"
    header Cross-Origin-Embedder-Policy "require-corp"
}

Обмеження ресурсів

services:
  bentopdf:
    image: ghcr.io/alam00000/bentopdf-simple:latest
    deploy:
      resources:
        limits:
          cpus: '1'
          memory: 512M
        reservations:
          cpus: '0.25'
          memory: 128M

Podman Quadlet (інтеграція із systemd)

Quadlet дає змогу запускати контейнери Podman як сервіси systemd. Це ідеально для робочих розгортань на системах Linux.

Базове налаштування Quadlet

Створіть файл юніта контейнера в ~/.config/containers/systemd/bentopdf.container (користувацький) або /etc/containers/systemd/bentopdf.container (системний):

[Unit]
Description=BentoPDF - Privacy-first PDF toolkit
After=network-online.target
Wants=network-online.target

[Container]
Image=ghcr.io/alam00000/bentopdf-simple:latest
ContainerName=bentopdf
PublishPort=3000:8080
AutoUpdate=registry

[Service]
Restart=always
TimeoutStartSec=300

[Install]
WantedBy=default.target

Увімкнення і запуск

# Reload systemd to detect new unit
systemctl --user daemon-reload

# Start the service
systemctl --user start bentopdf

# Enable on boot
systemctl --user enable bentopdf

# Check status
systemctl --user status bentopdf

# View logs
journalctl --user -u bentopdf -f

Tip

Для розгортання на рівні системи використовуйте systemctl без прапорця --user і помістіть файл у /etc/containers/systemd/.

Quadlet із перевіркою стану

[Unit]
Description=BentoPDF with health monitoring
After=network-online.target
Wants=network-online.target

[Container]
Image=ghcr.io/alam00000/bentopdf-simple:latest
ContainerName=bentopdf
PublishPort=3000:8080
AutoUpdate=registry
HealthCmd=wget --spider -q http://localhost:8080 || exit 1
HealthInterval=30s
HealthTimeout=10s
HealthRetries=3

[Service]
Restart=always
TimeoutStartSec=300

[Install]
WantedBy=default.target

Автоматичне оновлення з Quadlet

Podman може автоматично оновлювати контейнери, коли з'являються нові образи:

# Enable auto-update timer
systemctl --user enable --now podman-auto-update.timer

# Check for updates manually
podman auto-update

# Dry run (check without updating)
podman auto-update --dry-run

Налаштування мережі Quadlet

Для власної конфігурації мережі створіть файл мережі bentopdf.network:

[Network]
Subnet=10.89.0.0/24
Gateway=10.89.0.1

Потім послайтеся на нього у файлі контейнера:

[Container]
Image=ghcr.io/alam00000/bentopdf-simple:latest
ContainerName=bentopdf
PublishPort=3000:8080
Network=bentopdf.network

Оновлення

# Pull latest image
docker compose pull

# Recreate container
docker compose up -d