LoginSignup
5

More than 3 years have passed since last update.

GitHub Actions で Latexmk&タグを使ってコンパイルする TeX ファイルを指定する話

Last updated at Posted at 2019-12-12

概要

これまで筆者は

に挑戦してきた.

しかし,上に挙げた記事内の方法ではコンパイルが一度しか実行されない.従って,相互参照を含んでいたり BibTeX を利用していたりする場合,生成される PDF ファイルは (??) を含むなど不完全なものとなる.そこで,一度実行すれば自動的に必要なだけコンパイルをやってくれる Latexmk を利用して,この問題を解決する.

また,上に挙げた記事内の方法ではひとつの TeX ファイルのコンパイルにしか対応していなかった.これはコードの中でコンパイルする TeX ファイルを指定していたからである.そこで,コードでファイルを指定するのではなく,Git の機能の一つであるタグを用いてファイルを指定することで,この問題を解決する.

詳細

コンパイルさせたいファイルをタグ名で指定するため,タグ名は必ず ファイル名-ver.x にする.例えば doc1.tex というファイルをコンパイルさせたいなら,タグ名は doc1-ver.1 などとする.

必要ファイルの準備

下記の通り,必要最低限のファイルを用意する.同じものがこのリポジトリにある.

ファイルツリー
.
│  .latexmkrc
│
└─.github
    ├─actions
    │  └─latex
    │          Dockerfile
    │          entrypoint.sh
    │
    └─workflows
            latexmk.yml

.latexmkrc

.latexmkrc は Latexmk 実行時に何1を使ってコンパイルするかを記述したファイルである.

.latexmkrc
$latex  = 'platex -synctex=1 %O %S';
$bibtex = 'pbibtex %O %B';
$dvipdf = 'dvipdfmx %O -o %D %S';

Dockerfile

Dockerfile にはアクション実行時に行われる動作が一通り書かれている.

Dockerfile
FROM ubuntu:latest

RUN apt-get update \
  && apt-get install -y --no-install-recommends \
    curl \
    python3 \
    latexmk \
    lmodern \
    texlive \
    texlive-latex-extra \
    texlive-lang-japanese \
  && rm -rf /var/lib/apt/lists/*

RUN mktexlsr && mkdir -p /app
WORKDIR /app

ADD entrypoint.sh /entrypoint.sh
RUN ["chmod", "+x", "/entrypoint.sh"]
ENTRYPOINT ["/entrypoint.sh"]

entrypoint.sh

entrypoint.shDockerfile の最後で実行されるシェルスクリプトである.Latexmk の実行と,生成された PDF ファイルのリリース実行が書かれている.
3行目の GITHUB_REF には refs/tags/タグ名 という値が代入されているので,最初の10文字を排除して TAG_NAME としている.また,TAG_NAMEファイル名-ver.x という形に決めていたので,4行目では後ろから見て最初のハイフン以降を排除して FILE_NAME としている.

entrypoint.sh
#!/bin/bash
set -eux
TAG_NAME=${GITHUB_REF:10}
FILE_NAME=${TAG_NAME%-*}

# build pdf (change if necessary)
latexmk -pdfdvi $FILE_NAME.tex

# create release
res=`curl -H "Authorization: token $GITHUB_TOKEN" -X POST https://api.github.com/repos/$GITHUB_REPOSITORY/releases \
-d "
{
  \"tag_name\": \"$TAG_NAME\",
  \"target_commitish\": \"$GITHUB_SHA\",
  \"name\": \"$TAG_NAME\",
  \"draft\": false,
  \"prerelease\": false
}"`

# extract release id
rel_id=`echo ${res} | python3 -c 'import json,sys;print(json.load(sys.stdin)["id"])'`

# upload built pdf
curl -H "Authorization: token $GITHUB_TOKEN" -X POST https://uploads.github.com/repos/$GITHUB_REPOSITORY/releases/${rel_id}/assets?name=$FILE_NAME.pdf\
  --header 'Content-Type: application/pdf'\
  --upload-file $FILE_NAME.pdf

latexmk.yml

latexmk.yml にはアクションの場所や実行される条件が記述されている.実行条件は

  • push された中身に TeX ファイルが含まれていること
  • タグ名が *-ver.* の形になっていること

としている.

latexmk.yml
name: LaTeX to PDF (Latexmk)

on:
  push:
    paths: '*.tex'
    tags: '*-ver.*'

jobs:
  build:
    name: Build
    runs-on: ubuntu-latest
    steps:
      - name: Set up Git repository
        uses: actions/checkout@v1
      - name: Build docker image
        uses: denkiuo604/latexmk/.github/actions/latex@master
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

これでアクション実行に必要なファイルは揃う.

いざリリース

コンパイルしたい TeX ファイルを .latexmkrc と同じディレクトリに配置する.このリポジトリでは,例えば次のファイルを用いている.

doc2.tex
\documentclass{jsarticle}
\usepackage{amssymb}

\begin{document}

$(S,\Sigma,\mu)$を測度空間とする.
このとき,相異なる$i,j$に対して$A_i\cap A_j\neq\varnothing$を満たす
任意の$A_1,A_2,\cdots\in\Sigma$に対して
\begin{equation}\label{可算加法性}
    \mu\left(\bigcup_{k=1}^\infty A_k\right)=\sum_{k=1}^\infty\mu(A_k)
\end{equation}
が成り立つ.
また,(\ref{可算加法性})において$A_{n+1}=A_{n+2}=\cdots=\varnothing$とすることで
\begin{equation}\label{有限加法性}
    \mu\left(\bigcup_{k=1}^nA_k\right)=\sum_{k=1}^n\mu(A_k)
\end{equation}
も得られる.

\end{document}

上記 doc2.tex は相互参照を含むため,コンパイルを少なくとも2回実行しなければならない.しかし,Latexmk を使えば必要回数だけ自動でコンパイルしてくれる.

TeX ファイルを配置できたら,タグ名のルールに注意して push すればよい.今の場合,タグ名は doc2-ver.1 などとする.実際の結果は GitHub リポジトリを参照のこと.

参考


  1. platex か latex か,pbibtex か bibtex かなど.ここでは最低限の設定のみしている. 

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
What you can do with signing up
5