AI

OSSのPDFツール比較:Stirling-PDF vs LibreOffice vs OCRmyPDF でPDF処理をセルフホスト

オープンソースラボ編集部2026年6月13日

OSSのPDFツール比較:Stirling-PDF vs LibreOffice vs OCRmyPDF でPDF処理をセルフホスト

Adobe Acrobatは月$19.99/ユーザー、Small PDF・IlovePDFも月$6〜18と、PDFの変換・編集・OCRにはコストがかかります。Stirling-PDF(Docker製の多機能WebUI)・LibreOffice(オフィススイート)・OCRmyPDF(テキスト化)はOSSのPDF処理ツールです。セルフホストまたはCLIで無料・プライバシー安全にPDFを処理できます。

OSSのPDFツールを選ぶ理由

  • コスト削減: Adobe Acrobat月$19.99 × 50名 = $1,000/月をゼロに
  • プライバシー: 機密PDFを外部SaaSに送らずローカル・社内サーバーで処理
  • バッチ処理: 数百〜数千のPDFを自動化スクリプトで一括処理
  • CI/CDへの統合: PDF生成・変換をパイプラインに組み込む
  • カスタマイズ: ウォーターマーク追加・ページ分割・フォームデータ抽出を自動化

主要ツールの概要

Stirling-PDF

複数のOSSライブラリ(Ghostscript・LibreOffice・Tesseract・PDFBox・qpdf)をバックエンドに持つ、PDF処理の多機能WebUIです。GitHubスター55k+。30種類以上のPDF操作(マージ・スプリット・圧縮・変換・OCR・ウォーターマーク・電子署名・フォーム抽出等)をブラウザから操作でき、REST APIも内蔵しているのでバックエンドからプログラムで呼び出せます。

# Stirling-PDFをDockerで起動
docker run -d   --name stirling-pdf   --restart unless-stopped   -p 8080:8080   -v /opt/stirling-pdf/trainingData:/usr/share/tesseract-ocr/5/tessdata   -v /opt/stirling-pdf/extraConfigs:/configs   -v /opt/stirling-pdf/customFiles:/customFiles   -v /opt/stirling-pdf/logs:/logs   -e DOCKER_ENABLE_SECURITY=false   -e INSTALL_BOOK_AND_ADVANCED_HTML_OPS=false   -e LANGS=ja_JP   frooodle/s-pdf:latest

# または日本語OCR対応版
docker run -d   --name stirling-pdf   -p 8080:8080   -v $(pwd)/tessdata:/usr/share/tesseract-ocr/5/tessdata   -e INSTALL_BOOK_AND_ADVANCED_HTML_OPS=true   frooodle/s-pdf:latest

# 日本語OCRデータをダウンロード
docker exec stirling-pdf bash -c   "wget -O /usr/share/tesseract-ocr/5/tessdata/jpn.traineddata https://github.com/tesseract-ocr/tessdata_best/raw/main/jpn.traineddata"
# Stirling-PDF REST APIをPythonから使用する例
import requests

STIRLING_URL = "http://localhost:8080"

# 複数PDFをマージ
def merge_pdfs(pdf_paths: list, output_name: str) -> bytes:
    files = [('fileInput', (f'file{i}.pdf', open(p, 'rb'), 'application/pdf'))
             for i, p in enumerate(pdf_paths)]
    res = requests.post(
        f"{STIRLING_URL}/api/v1/general/merge-pdfs",
        files=files
    )
    return res.content

# PDFを圧縮
def compress_pdf(pdf_path: str, compression_level: str = "medium") -> bytes:
    with open(pdf_path, 'rb') as f:
        res = requests.post(
            f"{STIRLING_URL}/api/v1/general/compress-pdf",
            files={'fileInput': ('input.pdf', f, 'application/pdf')},
            data={'optimizeLevel': compression_level}  # low/medium/high/extreme
        )
    return res.content

# PDFをOCR処理してテキスト検索可能にする(日本語)
def ocr_pdf(pdf_path: str) -> bytes:
    with open(pdf_path, 'rb') as f:
        res = requests.post(
            f"{STIRLING_URL}/api/v1/misc/ocr-pdf",
            files={'fileInput': ('input.pdf', f, 'application/pdf')},
            data={'languages': 'jpn', 'ocrType': 'normal'}
        )
    return res.content

# PDFをWordに変換
def pdf_to_word(pdf_path: str) -> bytes:
    with open(pdf_path, 'rb') as f:
        res = requests.post(
            f"{STIRLING_URL}/api/v1/convert/pdf/word",
            files={'fileInput': ('input.pdf', f, 'application/pdf')},
            data={'outputFormat': 'docx'}
        )
    return res.content

# バッチ処理: フォルダ内の全PDFを圧縮
import os
from pathlib import Path

def batch_compress(input_dir: str, output_dir: str):
    Path(output_dir).mkdir(parents=True, exist_ok=True)
    for pdf_file in Path(input_dir).glob("*.pdf"):
        print(f"圧縮中: {pdf_file.name}")
        compressed = compress_pdf(str(pdf_file))
        output_path = Path(output_dir) / pdf_file.name
        with open(output_path, 'wb') as out:
            out.write(compressed)
        original_mb = pdf_file.stat().st_size / 1024 / 1024
        compressed_mb = len(compressed) / 1024 / 1024
        print(f"  {original_mb:.1f}MB → {compressed_mb:.1f}MB ({(1 - compressed_mb/original_mb)*100:.0f}%削減)")

LibreOffice(CLIモード)

LibreOfficeはGUIオフィススイートとして有名ですが、libreoffice --headless でサーバー環境でのバッチ変換に使えます。Word・Excel・PowerPointからPDFへの変換が最も品質が高く、従来フォントを含む複雑なレイアウトの再現性が高い。

# LibreOfficeをDockerでインストール
docker run -it --rm   -v $(pwd):/workspace   ubuntu:22.04 bash -c "    apt-get update &&     apt-get install -y libreoffice --no-install-recommends &&     libreoffice --headless --convert-to pdf /workspace/document.docx --outdir /workspace/output"
# Pythonでliboffice CLIを使ってバッチ変換
import subprocess
from pathlib import Path

def convert_to_pdf(input_path: str, output_dir: str) -> str:
    '''Word/Excel/PowerPoint → PDF 変換'''
    output = Path(output_dir)
    output.mkdir(parents=True, exist_ok=True)

    result = subprocess.run(
        ['libreoffice', '--headless', '--convert-to', 'pdf',
         '--outdir', str(output), input_path],
        capture_output=True,
        text=True,
        timeout=60
    )

    if result.returncode != 0:
        raise RuntimeError(f"変換エラー: {result.stderr}")

    # 出力ファイルパスを計算
    input_name = Path(input_path).stem
    return str(output / f"{input_name}.pdf")

# 例: フォルダ内の全.docxをPDFに変換
def batch_convert(input_dir: str, output_dir: str, extensions: list = ['.docx', '.xlsx', '.pptx']):
    for ext in extensions:
        for f in Path(input_dir).glob(f'*{ext}'):
            try:
                out = convert_to_pdf(str(f), output_dir)
                print(f"✓ {f.name} → {Path(out).name}")
            except Exception as e:
                print(f"✗ {f.name}: {e}")

OCRmyPDF

スキャンPDF(画像PDF)にテキストレイヤーを追加してPDF検索・コピーを可能にするOSSです。GitHubスター13k+。TesseractをバックエンドにPDF/A形式への変換・ページの傾き補正・圧縮を行います。大量の紙帳票・契約書・領収書をデジタル化する業務に最適です。

# OCRmyPDFをインストール(Ubuntu)
apt-get install -y ocrmypdf tesseract-ocr-jpn

# 基本的なOCR処理(日本語)
ocrmypdf --language jpn input_scan.pdf output_ocr.pdf

# 傾き補正 + 品質最適化 + PDF/A変換
ocrmypdf   --language jpn   --rotate-pages   --deskew   --clean   --optimize 1   --output-type pdfa   scanned_contract.pdf   output/contract_searchable.pdf

# バッチ処理(フォルダ内全スキャンをOCR化)
for f in /scans/*.pdf; do
  base=$(basename "$f" .pdf)
  ocrmypdf --language jpn --deskew --optimize 1 "$f" "/output/${base}_ocr.pdf"
  echo "Done: $base"
done
# OCRmyPDFをPythonプロセスから呼び出してLLMに送る
import subprocess
import anthropic
import tempfile
import pdfplumber  # pip install pdfplumber

def scan_pdf_to_text(pdf_path: str) -> str:
    '''スキャンPDFをOCRして全テキストを抽出'''
    with tempfile.NamedTemporaryFile(suffix='.pdf', delete=False) as tmp:
        tmp_path = tmp.name

    # OCR処理
    subprocess.run([
        'ocrmypdf', '--language', 'jpn', '--deskew', '--optimize', '1',
        pdf_path, tmp_path
    ], check=True, capture_output=True)

    # テキスト抽出
    with pdfplumber.open(tmp_path) as pdf:
        text = '

'.join(page.extract_text() or '' for page in pdf.pages)

    return text

def ask_about_contract(pdf_path: str, question: str) -> str:
    '''契約書PDFについてClaude APIに質問する'''
    contract_text = scan_pdf_to_text(pdf_path)

    client = anthropic.Anthropic()
    response = client.messages.create(
        model='claude-sonnet-4-6',
        max_tokens=2048,
        messages=[{
            'role': 'user',
            'content': f'以下の契約書の内容を分析してください。

{contract_text}

質問: {question}'
        }]
    )
    return response.content[0].text

機能比較表

比較項目Stirling-PDFLibreOfficeOCRmyPDF
ライセンスGPL-3.0MPL-2.0MPL-2.0
WebUI❌(CLI)❌(CLI)
REST API
Office→PDF変換✅(高品質)
スキャンOCR✅(Tesseract)✅(専門)
PDF圧縮
PDF結合・分割
Docker対応

PDF処理を自動化するパイプラインはDevOpsカテゴリ/categories/devopsのCI/CDツール比較も参照してください。PDFをLLMで分析するパターンはLLMツールカテゴリ/categories/llm-toolsにまとめています。

FAQ

Q. Stirling-PDFは社内のセキュリティポリシー上、外部にデータを送りますか?

A. セルフホストしたStirling-PDFは一切の外部通信を行いません。処理はすべてローカルのDockerコンテナ内で完結します。確認方法: docker inspect stirling-pdfでネットワーク設定を確認するか、DockerをInternalネットワークのみに接続させることでさらに確実に外部通信を遮断できます。-e DOCKER_ENABLE_SECURITY=trueを設定するとログイン認証が有効になり、社内ユーザーのみがアクセスできるよう制限できます。NginxでIPアドレス制限を追加することも推奨します。

Q. スキャンした日本語の契約書をOCR処理する際の精度はどのくらいですか?

A. Tesseract(OCRmyPDFのバックエンド)の日本語OCR精度は、スキャン品質と設定によって大きく変わります。精度が高い条件: ①スキャン解像度300dpi以上②文書が水平・傾きなし③フォントが明朝体・ゴシック体(標準的な印刷フォント)④背景が白で文字が黒。精度が低くなる条件: ①手書き文字(Tesseractは手書き認識が苦手)②特殊フォント・ロゴ・押印③コピーを重ねたような劣化スキャン。実測精度: 良質な印刷契約書のスキャン→漢字・ひらがな・数字で95%以上。スタンプ・手書き欄→50〜70%程度。精度を上げるにはtesseract_bestモデル(jpn.traineddataの精度最高版)を使い、前処理(画像の2値化・ノイズ除去)を追加します。

Q. LibreOfficeでWord→PDF変換したときに日本語フォントが崩れる場合の対処は?

A. フォント崩れの主な原因はDockerコンテナにWindowsフォントがないためです。対処法: ①Notoフォントをインストール: apt-get install -y fonts-noto-cjkでほとんどの日本語フォントをカバーできます②MS互換フォントをコンテナにコピー: 社内の場合、Windows PCからIPAフォント・源ノ角ゴシック等を取得してコンテナの/usr/share/fonts/にコピーしfc-cache -fを実行③フォントキャッシュの更新: Dockerビルド時にRUN fc-cache -fを実行。Dockerfileの例:

FROM ubuntu:22.04
RUN apt-get update && apt-get install -y     libreoffice     fonts-noto-cjk     fonts-noto-cjk-extra     --no-install-recommends     && fc-cache -f     && rm -rf /var/lib/apt/lists/*
ENTRYPOINT ["libreoffice", "--headless"]

Q. Next.jsアプリからPDFを動的生成するのにStirling-PDFは適していますか?

A. HTML→PDFの動的生成にはStirling-PDFより**Puppeteer・Playwright・または@react-pdf/renderer**の方が適しています。Stirling-PDFは「既存のファイルを変換・操作する」ツールであり、「HTMLテンプレートからPDFを生成する」用途は本来の設計外です。用途別の推奨:

// Next.js API Routeで請求書PDFを動的生成(react-pdf)
// npm install @react-pdf/renderer

import { renderToBuffer } from '@react-pdf/renderer';
import { Document, Page, Text, View, StyleSheet } from '@react-pdf/renderer';

const InvoicePDF = ({ invoice }: { invoice: Invoice }) => (
  <Document>
    <Page size="A4" style={{ padding: 40 }}>
      <View style={{ marginBottom: 20 }}>
        <Text style={{ fontSize: 24, fontWeight: 'bold' }}>請求書</Text>
        <Text>請求番号: {invoice.number}</Text>
      </View>
      {/* ... */}
    </Page>
  </Document>
);

export async function GET(req: Request) {
  const invoice = await getInvoice(req);
  const buffer = await renderToBuffer(<InvoicePDF invoice={invoice} />);
  return new Response(buffer, {
    headers: {
      'Content-Type': 'application/pdf',
      'Content-Disposition': `attachment; filename="invoice-${invoice.number}.pdf"`,
    },
  });
}

Stirling-PDFは「ユーザーがアップロードしたPDFを圧縮・変換する」バックエンドとして活用し、動的生成は専用のPDFライブラリを使うのがベストプラクティスです。

まとめ

ユースケース推奨ツール
PDF操作・変換の多機能WebUIStirling-PDF
Office→PDF高品質変換LibreOffice CLI
スキャンOCR・テキスト化OCRmyPDF
動的PDF生成react-pdf / Puppeteer

関連外部リソース

他の記事も読む

Let's Build Together

OSS導入、自社だけで悩まない。

ツール選定から構築・運用・AI活用まで、オープンソースラボ運営元のClasslessが伴走します。初回のご相談は無料です。