6
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

ODA SDKのDockerでの環境構築と日本語文字の取り扱い

6
Posted at

Autodesk DWGをODA SDKでDXFに変換する方法(Docker + Python)

本記事では、Autodesk独自のCADファイル形式であるDWGを、オープンな規格であるDXFに変換する環境構築の手順を紹介します。今回はDocker環境上でPythonアプリケーションとして実装する方法をまとめました。

ライセンスと費用についての注意点

ODA SDKをアプリケーションに組み込んで商用利用する場合、Commercialライセンスの契約が必要です。費用は初年度が$3,000、次年度以降は年間$2,250となりますが、クレジットカード決済には対応していないそうです。

もし、検証目的のみで利用したい場合は、60日間のFree Trialが利用できます。ただし、Free TrialはWindows版のみの提供であり、Linux版とはディレクトリ構造が異なる点に注意が必要です。Linuxなど他のOSで本格的な検証を行いたい場合は、Non-Commercialライセンス(初年度$375、年間$150)の利用を検討することになります。

Pythonでの開発環境について

Pythonでの実装はSWIGによるラッパーを利用する形となります。現時点では公式のPythonAPIドキュメントは見つける事ができませんでした。また、Free Trial版などでは一部のクラスがラップされていないケースもあります。そのため、Pythonでの実装にあたってはC++のドキュメントを読み解く必要があり、少々手探りな作業になることをあらかじめ念頭に置いておくと良いでしょう。

Linux上での環境構築手順

Linux環境向けには、「dll」というプレフィックスが付いた動的リンクライブラリ版を使用するのが、Free Trial環境の構成に最も近く扱いやすいです。

必要なファイルとして、Kernel SDKとDrawing SDKそれぞれの「通常版」「.NET版」「Python版」を用意します。なお、ダウンロードしたファイルは拡張子が「.tar.gz」となっていても、実際にはただの「.tar」である場合があるので注意してください。これらに加え、アクティベーションコード(OdActivationInfo.py)も必要です。

必要なファイル構成例

ODASDK/
├── Drawings.NET_lnxX64_8.3dll_26.10.tar.gz
├── Drawings.PY3_lnxX64_8.3dll_26.10.tar.gz
├── Drawings_lnxX64_8.3dll_26.10.tar.gz
├── Kernel.NET_lnxX64_8.3dll_26.10.tar.gz
├── Kernel.PY3_lnxX64_8.3dll_26.10.tar.gz
├── Kernel_lnxX64_8.3dll_26.10.tar.gz
└── OdActivationInfo.py

上記のファイルを適当なディレクトリに格納し、一括で解凍・配置を行うシェルスクリプトを作成すると作業がスムーズです。以下にセットアップ用のスクリプト例を記載します。

#!/bin/bash

# ODA SDK Setup Script for Linux
# This script extracts ODA SDK tar.gz files and sets up the environment

set -e  # Exit on error

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
ODASDK_DIR="${SCRIPT_DIR}/ODASDK"
INSTALL_DIR="${SCRIPT_DIR}/ODAToolkit"

echo "=== ODA SDK Setup for Linux ==="
echo "Script directory: ${SCRIPT_DIR}"
echo "ODASDK directory: ${ODASDK_DIR}"
echo "Install directory: ${INSTALL_DIR}"
echo ""

# Check if ODASDK directory exists
if [ ! -d "${ODASDK_DIR}" ]; then
    echo "Error: ODASDK directory not found at ${ODASDK_DIR}"
    exit 1
fi

# Create installation directory
mkdir -p "${INSTALL_DIR}"

# Find and extract tar.gz files
echo "Searching for tar.gz files..."
TAR_GZ_FILES=$(find "${ODASDK_DIR}" -name "*.tar.gz" -type f)

if [ -z "${TAR_GZ_FILES}" ]; then
    echo "Warning: No tar.gz files found in ${ODASDK_DIR}"
    echo "Searching for .tar files..."
    TAR_FILES=$(find "${ODASDK_DIR}" -name "*.tar" -type f)

    if [ -z "${TAR_FILES}" ]; then
        echo "Error: No .tar or .tar.gz files found"
        exit 1
    fi

    # Extract .tar files
    echo "Found .tar files:"
    echo "${TAR_FILES}"
    echo ""

    for TAR_FILE in ${TAR_FILES}; do
        echo "Extracting: $(basename ${TAR_FILE})"
        tar -xf "${TAR_FILE}" -C "${INSTALL_DIR}"
        echo "Done: $(basename ${TAR_FILE})"
        echo ""
    done
else
    # Extract .tar.gz files
    echo "Found tar.gz files:"
    echo "${TAR_GZ_FILES}"
    echo ""

    for TAR_GZ_FILE in ${TAR_GZ_FILES}; do
        echo "Extracting: $(basename ${TAR_GZ_FILE})"
        tar -xzf "${TAR_GZ_FILE}" -C "${INSTALL_DIR}"
        echo "Done: $(basename ${TAR_GZ_FILE})"
        echo ""
    done
fi

# Copy activation info
if [ -f "${ODASDK_DIR}/OdActivationInfo.py" ]; then
    echo "Copying OdActivationInfo.py..."
    mkdir -p "${INSTALL_DIR}/activation"
    cp "${ODASDK_DIR}/OdActivationInfo.py" "${INSTALL_DIR}/activation/"
    echo "Done"
    echo ""
fi

# Display extracted structure
echo "=== Extraction Complete ==="
echo "Installed to: ${INSTALL_DIR}"
echo ""
echo "Directory structure:"
ls -la "${INSTALL_DIR}"
echo ""

# Check for common directories
if [ -d "${INSTALL_DIR}/bin" ]; then
    echo "Found bin directory:"
    ls -la "${INSTALL_DIR}/bin" | head -20
    echo ""
fi

if [ -d "${INSTALL_DIR}/lib" ]; then
    echo "Found lib directory:"
    ls -la "${INSTALL_DIR}/lib" | head -20
    echo ""
fi

echo ""
echo "=== Setup Complete ==="

Dockerでの実装準備

解凍して作成されたディレクトリ(ODAToolkitなど)をDockerイメージ内の特定ディレクトリにコピーし、環境変数 LD_LIBRARY_PATH を通します。

Dockerfile

# Copy ODA SDK files
COPY ODAToolkit /app/ODAToolkit
# ODA_SDK_PATH should point to the directory containing ODAToolkit folder
ENV LD_LIBRARY_PATH=/app/ODAToolkit/bin/lnxX64_8.3dll:$LD_LIBRARY_PATH

なお、SDKのバイナリを含めるとファイルサイズが4GB程度になるため、Gitなどで管理する場合は .gitignore にSDKの格納ディレクトリを指定しておくことを推奨します。

/converter/ODASDK
/converter/ODAToolkit

Pythonによる実装

Pythonコード側でも、SDKのパスを環境変数として設定します。

oda_sdk_base_path: str = os.getenv("ODA_SDK_PATH")
os.environ["LD_LIBRARY_PATH"] = oda_sdk_base_path + os.environ.get("LD_LIBRARY_PATH", "")

パス設定後、必要なライブラリをインポートできるようになります。

# Import ODA modules (after path is set)
from OdActivationInfo import ActivationData
from ODA_Drawings_Py3 import odInitialize
from ODA_Kernel_Py3 import RxSystemServicesImpl, odActivate
from ODA_PyMemManager_Py3 import ODA_PyMemoryManager_Get_MemoryManager

初期化とアクティベーション

SDKを使用するには初期化とアクティベーションが必要です。これについてはドキュメントにサンプルコードが存在します。

# Start memory transaction
_oda_transaction = ODA_PyMemoryManager_Get_MemoryManager().StartTransaction()

# Define custom SystemServices class
class SystemServices(RxSystemServicesImpl):
    def __init__(self):
        RxSystemServicesImpl.__init__(self)
        odActivate(ActivationData.userInfo, ActivationData.userSignature)

# Initialize
_oda_system_services = SystemServices()
odInitialize(_oda_system_services)

変換処理の実装

変換ロジックについては、C++のAPIドキュメントを参照しながら実装します。 ODA_Drawings_Py3.pyODA_Kernel_Py3.py といったファイルをLLM(大規模言語モデル)などに読み込ませると、比較的スムーズにPythonコードへ変換してくれます。

以下は実装の一例です。

# Import ODA modules
import ODA_Drawings_Py3
import ODA_Kernel_Py3

# Create host application services
hostApp = ODA_Drawings_Py3.ExHostAppServices()

# Read input file (DWG/DXF/DXB)
db = hostApp.readFile(
    str(input_path),
    True,  # bAllowCPConversion
    False,  # bPartial
    ODA_Kernel_Py3.kShareDenyNo,
    "",  # password
)

# Audit the database and fix errors if requested
if fix_errors:
    audit_info = ODA_Drawings_Py3.OdDbAuditInfo()
    audit_info.setFixErrors(True)
    audit_info.setPrintDest(ODA_Drawings_Py3.OdDbAuditInfo.kBoth)

    db.auditDatabase(audit_info)

    num_errors = audit_info.numErrors()
    num_fixes = audit_info.numFixes()

    if num_errors > 0:
        logger.warning(f"Errors found: {num_errors}")
        logger.info(f"Errors fixed: {num_fixes}")
    else:
        logger.info("No errors found in database")

# Determine save type
save_type_map = {
    "DWG": ODA_Drawings_Py3.OdDb_SaveType_kDwg,
    "DXF": ODA_Drawings_Py3.OdDb_SaveType_kDxf,  # ASCII format
    "DXB": ODA_Drawings_Py3.OdDb_SaveType_kDxb,  # Binary DXF format
}
save_type = save_type_map.get(
    format_type_upper, ODA_Drawings_Py3.OdDb_SaveType_kDxf
)

# Determine output version
version_map = {
    "R9": ODA_Kernel_Py3.vAC09,  # DXF/DXB only
    "R10": ODA_Kernel_Py3.vAC10,  # DXF/DXB only
    "R12": ODA_Kernel_Py3.vAC12,
    "R13": ODA_Kernel_Py3.vAC13,
    "R14": ODA_Kernel_Py3.vAC14,
    "R2000": ODA_Kernel_Py3.vAC15,
    "R2004": ODA_Kernel_Py3.vAC18,
    "R2007": ODA_Kernel_Py3.vAC21,
    "R2010": ODA_Kernel_Py3.vAC24,
    "R2013": ODA_Kernel_Py3.vAC27,
    "R2018": ODA_Kernel_Py3.vAC32,
}

output_version = version_map.get(dxf_version.upper(), ODA_Kernel_Py3.vAC32)

# Write file (using filepath string)
db.writeFile(
    str(output_path),
    save_type,
    output_version,
    generate_thumbnail,  # Generate thumbnail
)

return output_path

最後に、終了処理も忘れずに行います。

from ODA_Drawings_Py3 import odUninitialize
odUninitialize()

以上で、ODA SDKを用いた変換環境の構築は完了です。

ODA SDKにおけるLinux上での日本語フォントの取り扱い

Linux環境のODA SDKで図面内の日本語を正しく表示・変換させるには、DWGファイルと同じディレクトリにフォントファイル(.ttfなど)を配置する必要があります。

特に問題となるのが、Windows環境で標準的に使われている「MSゴシック」などのフォントコレクション(.ttc)です。これらは商用フォントであるため、Linux環境にそのままコピーして利用することはライセンス上の制約で難しい場合があります。そこで、IPAフォントなどのフリーフォントをベースに、MSゴシック等と同じ内部名を持つ代替の.ttcファイルを自作する手法が有効です。

IPAフォントから代替TTCファイルを作成する

Pythonの fontTools ライブラリを使用して、IPAフォントを元にWindowsの標準フォント(MSゴシック、メイリオなど)として認識されるTTCファイルを生成するスクリプトを作成しました。このスクリプトは、既存のIPAフォントのフォント名を書き換え、Windows標準のTTCファイルと同じ構造を持ったファイルを出力します。

必要なライブラリのインストール

pip install fonttools

フォント生成スクリプト(generate_ttc.py)

generate_ttc.py
#!/usr/bin/env python3
"""
Generate TTC files from IPA fonts to match Windows TTC structure.

This script creates TTC (TrueType Collection) files that have the same
number of fonts as the original Windows TTC files, using IPA fonts as
substitutes. Font names in the name table are updated to match Windows names.
"""

from fontTools.ttLib import TTCollection, TTFont
from pathlib import Path
import shutil
import sys

# Source IPA fonts
IPA_FONT_DIR = Path("font_src")
IPA_GOTHIC = IPA_FONT_DIR / "ipag.ttf"  # IPA Gothic (monospace)
IPA_GOTHIC_P = IPA_FONT_DIR / "ipagp.ttf"  # IPA Gothic Proportional
IPA_MINCHO = IPA_FONT_DIR / "ipam.ttf"  # IPA Mincho (monospace)
IPA_MINCHO_P = IPA_FONT_DIR / "ipamp.ttf"  # IPA Mincho Proportional

# Output directory
OUTPUT_DIR = Path("generated_fonts")

# TTC mapping: filename -> (list of (english_name, japanese_name) tuples, ipa_font_to_use)
# Each font name tuple corresponds to fonts in the TTC
TTC_MAPPING = {
    # Japanese Gothic fonts
    "msgothic.ttc": (
        [
            ("MS Gothic", "MS ゴシック"),
            ("MS UI Gothic", "MS UI Gothic"),
            ("MS PGothic", "MS Pゴシック"),
        ],
        IPA_GOTHIC,
    ),
    "meiryo.ttc": (
        [
            ("Meiryo", "メイリオ"),
            ("Meiryo Italic", "メイリオ Italic"),
            ("Meiryo UI", "Meiryo UI"),
            ("Meiryo UI Italic", "Meiryo UI Italic"),
        ],
        IPA_GOTHIC_P,
    ),
    "meiryob.ttc": (
        [
            ("Meiryo Bold", "メイリオ Bold"),
            ("Meiryo Bold Italic", "メイリオ Bold Italic"),
            ("Meiryo UI Bold", "Meiryo UI Bold"),
            ("Meiryo UI Bold Italic", "Meiryo UI Bold Italic"),
        ],
        IPA_GOTHIC_P,
    ),
    "YuGothB.ttc": (
        [
            ("Yu Gothic Bold", "游ゴシック Bold"),
            ("Yu Gothic UI Bold", "Yu Gothic UI Bold"),
            ("Yu Gothic UI Semibold", "Yu Gothic UI Semibold"),
        ],
        IPA_GOTHIC,
    ),
    "YuGothL.ttc": (
        [
            ("Yu Gothic Light", "游ゴシック Light"),
            ("Yu Gothic UI Light", "Yu Gothic UI Light"),
        ],
        IPA_GOTHIC,
    ),
    "YuGothM.ttc": (
        [
            ("Yu Gothic Medium", "游ゴシック Medium"),
            ("Yu Gothic UI Regular", "Yu Gothic UI Regular"),
        ],
        IPA_GOTHIC,
    ),
    "YuGothR.ttc": (
        [
            ("Yu Gothic Regular", "游ゴシック Regular"),
            ("Yu Gothic UI Semilight", "Yu Gothic UI Semilight"),
        ],
        IPA_GOTHIC,
    ),
    "BIZ-UDGothicB.ttc": (
        [
            ("BIZ UDGothic Bold", "BIZ UDゴシック Bold"),
            ("BIZ UDPGothic Bold", "BIZ UDPゴシック Bold"),
        ],
        IPA_GOTHIC,
    ),
    "BIZ-UDGothicR.ttc": (
        [("BIZ UDGothic", "BIZ UDゴシック"), ("BIZ UDPGothic", "BIZ UDPゴシック")],
        IPA_GOTHIC,
    ),
    # Japanese Mincho fonts
    "msmincho.ttc": (
        [("MS Mincho", "MS 明朝"), ("MS PMincho", "MS P明朝")],
        IPA_MINCHO,
    ),
    "BIZ-UDMinchoM.ttc": (
        [
            ("BIZ UDMincho Medium", "BIZ UD明朝 Medium"),
            ("BIZ UDPMincho Medium", "BIZ UDP明朝 Medium"),
        ],
        IPA_MINCHO,
    ),
    # Educational fonts (use Gothic)
    "UDDigiKyokashoN-B.ttc": (
        [
            ("UD Digi Kyokasho N-B", "UD デジタル 教科書体 N-B"),
            ("UD Digi Kyokasho NP-B", "UD デジタル 教科書体 NP-B"),
            ("UD Digi Kyokasho NK-B", "UD デジタル 教科書体 NK-B"),
        ],
        IPA_GOTHIC,
    ),
    "UDDigiKyokashoN-R.ttc": (
        [
            ("UD Digi Kyokasho N-R", "UD デジタル 教科書体 N-R"),
            ("UD Digi Kyokasho NP-R", "UD デジタル 教科書体 NP-R"),
            ("UD Digi Kyokasho NK-R", "UD デジタル 教科書体 NK-R"),
        ],
        IPA_GOTHIC,
    ),
    # Chinese fonts (use Gothic as fallback)
    "msjh.ttc": (
        [
            ("Microsoft JhengHei", "微軟正黑體"),
            ("Microsoft JhengHei UI", "Microsoft JhengHei UI"),
        ],
        IPA_GOTHIC_P,
    ),
    "msjhbd.ttc": (
        [
            ("Microsoft JhengHei Bold", "微軟正黑體 Bold"),
            ("Microsoft JhengHei UI Bold", "Microsoft JhengHei UI Bold"),
        ],
        IPA_GOTHIC_P,
    ),
    "msjhl.ttc": (
        [
            ("Microsoft JhengHei Light", "微軟正黑體 Light"),
            ("Microsoft JhengHei UI Light", "Microsoft JhengHei UI Light"),
        ],
        IPA_GOTHIC_P,
    ),
    "msyh.ttc": (
        [
            ("Microsoft YaHei", "Microsoft YaHei"),
            ("Microsoft YaHei UI", "Microsoft YaHei UI"),
        ],
        IPA_GOTHIC_P,
    ),
    "msyhbd.ttc": (
        [
            ("Microsoft YaHei Bold", "Microsoft YaHei Bold"),
            ("Microsoft YaHei UI Bold", "Microsoft YaHei UI Bold"),
        ],
        IPA_GOTHIC_P,
    ),
    "msyhl.ttc": (
        [
            ("Microsoft YaHei Light", "Microsoft YaHei Light"),
            ("Microsoft YaHei UI Light", "Microsoft YaHei UI Light"),
        ],
        IPA_GOTHIC_P,
    ),
    "mingliub.ttc": (
        [
            ("MingLiU-ExtB", "細明體-ExtB"),
            ("PMingLiU-ExtB", "新細明體-ExtB"),
            ("MingLiU_HKSCS-ExtB", "細明體_HKSCS-ExtB"),
            ("MingLiU_MSCS-ExtB", "細明體_MSCS-ExtB"),
        ],
        IPA_MINCHO,
    ),
    "simsun.ttc": ([("SimSun", "宋体"), ("NSimSun", "新宋体")], IPA_MINCHO),
    # Other fonts
    "cambria.ttc": (
        [("Cambria", "Cambria"), ("Cambria Math", "Cambria Math")],
        IPA_MINCHO_P,
    ),
    "Nirmala.ttc": (
        [
            ("Nirmala UI", "Nirmala UI"),
            ("Nirmala UI Bold", "Nirmala UI Bold"),
            ("Nirmala UI Semilight", "Nirmala UI Semilight"),
            ("Nirmala Text", "Nirmala Text"),
            ("Nirmala Text Bold", "Nirmala Text Bold"),
            ("Nirmala Text Semilight", "Nirmala Text Semilight"),
        ],
        IPA_GOTHIC_P,
    ),
}

def update_font_name(font: TTFont, new_name: str, japanese_name: str = None) -> None:
    """
    Update font name in the name table.

    Args:
        font: TTFont object to modify
        new_name: New font name to set (English)
        japanese_name: Japanese font name (optional, for Japanese locale)
    """
    name_table = font["name"]

    # Name IDs to update:
    # 1 = Font Family name
    # 4 = Full font name
    # 6 = PostScript name (no spaces)
    name_ids_to_update = [1, 4, 6]

    for record in name_table.names:
        if record.nameID in name_ids_to_update:
            if record.nameID == 6:
                # PostScript name: replace spaces with hyphens
                ps_name = new_name.replace(" ", "-")
                record.string = ps_name
            else:
                # Use Japanese name for Japanese locale (platformID=3, langID=1041)
                # Use English name for other locales
                if japanese_name and record.platformID == 3 and record.langID == 1041:
                    record.string = japanese_name
                else:
                    record.string = new_name

def create_ttc(
    output_path: Path, font_name_pairs: list, source_font_path: Path
) -> None:
    """
    Create a TTC file with specified font names.

    Args:
        output_path: Path to output TTC file
        font_name_pairs: List of (english_name, japanese_name) tuples for each font in the TTC
        source_font_path: Path to source TTF font to use
    """
    print(
        f"Creating {output_path.name} with {len(font_name_pairs)} fonts from {source_font_path.name}"
    )

    ttc = TTCollection()

    for i, (english_name, japanese_name) in enumerate(font_name_pairs):
        # Load fresh copy of the font for each entry
        font = TTFont(source_font_path)
        # Update the font name with both English and Japanese names
        update_font_name(font, english_name, japanese_name)
        ttc.fonts.append(font)
        print(f"  [{i}] {english_name} / {japanese_name}")

    ttc.save(str(output_path))
    print(f"  -> Created: {output_path}")

def main():
    # Create output directory
    OUTPUT_DIR.mkdir(exist_ok=True)

    print("=== Generating TTC files from IPA fonts ===\n")

    # Verify IPA fonts exist
    for font_path in [IPA_GOTHIC, IPA_GOTHIC_P, IPA_MINCHO, IPA_MINCHO_P]:
        if not font_path.exists():
            print(f"Error: IPA font not found: {font_path}")
            sys.exit(1)

    print(f"IPA fonts found in {IPA_FONT_DIR}\n")

    # Generate TTC files
    for ttc_name, (font_name_pairs, ipa_font) in TTC_MAPPING.items():
        output_path = OUTPUT_DIR / ttc_name
        create_ttc(output_path, font_name_pairs, ipa_font)

    print(f"\n=== Generation complete ===")
    print(f"Generated {len(TTC_MAPPING)} TTC files in {OUTPUT_DIR}/")

    # Also copy the original IPA TTF files
    print(f"\nCopying IPA TTF files to {OUTPUT_DIR}/...")
    for font_path in [IPA_GOTHIC, IPA_GOTHIC_P, IPA_MINCHO, IPA_MINCHO_P]:
        dest = OUTPUT_DIR / font_path.name
        shutil.copy(font_path, dest)
        print(f"  -> Copied: {font_path.name}")

    print("\nDone!")

if __name__ == "__main__":
    main()

このスクリプトを実行すると、generated_fonts ディレクトリに「msgothic.ttc」や「meiryo.ttc」といったファイルが生成されます。これらは実態としてはIPAフォントですが、ODA SDKからはWindows標準フォントとして認識されます。

Docker環境でのフォントマッピング

さらに、アプリケーション実行時にこれらのフォントを正しく読み込ませるため、Dockerコンテナのエントリーポイントでシンボリックリンクを作成する処理を行います。これにより、単一のIPAフォントファイルを複数のWindowsフォント名(Arial, Times New Roman等)にマッピングさせることが可能です。

以下のようなシェルスクリプトをエントリーポイントとして設定します。
エントリーポイント用スクリプト

entrypoint.sh
#!/bin/bash
set -e

# Font symlink setup for ODA SDK
# Creates symlinks in /app/temp directory at container startup
# to avoid race conditions during concurrent access

TEMP_DIR="/app/temp"
FONT_DIR="${ODA_FONT_PATH:-/app/fonts}"

echo "Setting up font symlinks in ${TEMP_DIR}..."

# Ensure temp directory exists
mkdir -p "${TEMP_DIR}"

# TTC font files (pre-generated)
TTC_FONTS=($(ls "${FONT_DIR}"/*.ttc 2>/dev/null | xargs -n1 basename))

# TTF font mappings (Windows font -> IPA font)
declare -A TTF_MAPPINGS=(
    # Korean fonts -> IPA Gothic Proportional
    ["malgun.ttf"]="ipagp.ttf"
    ["malgunbd.ttf"]="ipagp.ttf"
    # ... (中略) ...
    # Arial family -> IPA Gothic Proportional
    ["arial.ttf"]="ipagp.ttf"
    ["ariblk.ttf"]="ipagp.ttf"
    # ... (その他必要なマッピング) ...
)

# Create symlinks for TTC files
for ttc in "${TTC_FONTS[@]}"; do
    source="${FONT_DIR}/${ttc}"
    target="${TEMP_DIR}/${ttc}"
    if [ -f "${source}" ] && [ ! -e "${target}" ]; then
        ln -sf "${source}" "${target}"
        echo "  Created symlink: ${ttc}"
    fi
done

# Create symlinks for TTF mappings
for windows_font in "${!TTF_MAPPINGS[@]}"; do
    ipa_font="${TTF_MAPPINGS[$windows_font]}"
    source="${FONT_DIR}/${ipa_font}"
    target="${TEMP_DIR}/${windows_font}"
    if [ -f "${source}" ] && [ ! -e "${target}" ]; then
        ln -sf "${source}" "${target}"
        echo "  Created symlink: ${windows_font} -> ${ipa_font}"
    fi
done

echo "Font symlink setup completed."

# Execute the main command (uvicorn)
exec "$@"

エントリーポイントをコピーします。これによりフォントのシンボリックリンクがdwg格納ディレクトリに作られます。

COPY [entrypoint.sh](http://entrypoint.sh/) /app/entrypoint.sh
RUN chmod +x /app/entrypoint.sh

ENTRYPOINT ["/app/entrypoint.sh"]

この構成により、Dockerコンテナ内でもフォントのライセンス問題をクリアしつつ、図面変換時の文字化けやフォント置換エラーを最小限に抑えることができます。

6
1
0

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
  3. You can use dark theme
What you can do with signing up
6
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?