mkdocs-with-pdfは最終更新が2021年から更新が止まっているので情報が古かったです。
WeasyPrintを利用するライブラリとバージョン要件
WeasyPrintの情報を確認したところ、記事作成時点では以下の要件になっていました。
- Python ≥ 3.9.0
- Pango ≥ 1.44.0
- pydyf ≥ 0.10.0
- CFFI ≥ 0.6
- tinyhtml5 ≥ 2.0.0b1
- tinycss2 ≥ 1.3.0
- cssselect2 ≥ 0.1
- Pyphen ≥ 0.9.1
- Pillow ≥ 9.1.0
- fontTools ≥ 4.0.0
Docker環境準備
環境違いでマウントパスの書き方を変えるのが手間なので、compose.ymlも作成しています。
※カスタムのCSSやJavascript実行が必要な場合はヘッドレスChromeの環境も必要みたいです
Dockerfile 作成
FROM python:3.9
# 環境変数設定
ENV LANG=C.UTF-8 \
TZ=Asia/Tokyo \
DEBIAN_FRONTEND=noninteractive
# 必要なシステムライブラリをインストール
RUN apt-get update && apt-get install -y \
libpango-1.0-0 \
libpangoft2-1.0-0 \
libffi-dev \
libopenjp2-7-dev \
fonts-ipafont \
fonts-ipaexfont \
&& apt-get clean && rm -rf /var/lib/apt/lists/*
# python関連のライブラリ追加
RUN pip install --no-cache-dir \
weasyprint \
pydyf \
cffi \
tinyhtml5 \
tinycss2 \
cssselect2 \
pyphen \
pillow \
fonttools \
mkdocs \
mkdocs-material \
mkdocs-awesome-pages-plugin \
mdx-gh-links \
mkdocs-redirects \
mkdocs-minify-plugin \
weasyprint mkdocs-with-pdf
WORKDIR /docs
compose.yml 作成
services:
mkdocs:
container_name: mkdocs
build: .
volumes:
- .:/docs
mkdocsの設定ファイル変更
利用するプラグインにwith-pdf
を追加
※awesome-pages
より前に記載すると設定が上書きされると警告出るので最後に追加しました
mkdocs.yml
# --- (省略) ----
plugins:
- search
- awesome-pages:
collapse_single_pages: true
- with-pdf # ★この行を追加
PDF作成の実行
これでビルドして、PDF作成することができました。
あとは、オプションの調整をして見栄えをどうにかする必要があります。
$ docker compose run --rm mkdocs mkdocs build
# --- (docker build は長いので省略) ---
INFO - Cleaning site directory
INFO - Building documentation to directory: /docs/site
INFO - Number headings up to level 3.
INFO - Generate a table of contents up to heading level 2.
INFO - Generate a cover page with "default_cover.html.j2".
INFO - Converting <img> alignment(workaround).
INFO - Rendering for PDF.
INFO - Output a PDF to "/docs/site/pdf/document.pdf".
補足
最初、pythonのライブラリはバージョン指定でやっていたのですが、WeasyPrintが内部で使用しているpydyfライブラリのバージョン(pydyf==0.10.0
)で以下の警告出たので、バージョン指定はしていないです。
(環境を安定させるのにバージョンは指定しておいた方が良いけど後でやるつもり・・・
INFO - DeprecationWarning: PDF objects don’t take version or identifier during initialization anymore. These properties are now stored but ignored, and will be removed and rejected in next version of pydyf. Please pass these properties to the PDF.write()
method instead.
File "/usr/local/lib/python3.9/site-packages/weasyprint/pdf/__init__.py", line 119, in generate_pdf
pdf = pydyf.PDF((version or '1.7'), identifier)
File "/usr/local/lib/python3.9/site-packages/pydyf/__init__.py", line 450, in __init__