開発への貢献
[!NOTE] このページには contributor 向けの内部 import 例が含まれます。外部利用者向けの supported import path は
shogiarena.engine/shogiarena.tournament/shogiarena.cli/shogiarena.compositionです。
ShogiArena の開発に参加するための最小ガイドです。
セットアップ
git clone https://github.com/nyoki-mtl/ShogiArena.git
cd ShogiArena
uv sync
必要に応じて frontend 依存も入れます。
npm ci
よく使うコマンド
make format # コードフォーマット(ruff format)
make lint # リントチェック(ruff check --fix)
make typecheck # 型チェック(ty)
make check # format, lint, convention-lint, typecheck, check-js を実行(テストは含まない)
make test # 全テスト実行
make check-full # check + test + frontend-test
make ci # public GitHub CI と同等の検証
make ci-develop # develop GitHub CI と同等の検証(typing-audit含む)
ドキュメントは現在 mdBook です。
make docs-build # 静的ドキュメントのビルド
make docs-serve # ローカルサーバーで自動リロード付きプレビュー(ブラウザが開きます)
CI/CD と公開フロー
- private の
ShogiArena-devではdevelop-ci.ymlがmake ci-developを実行します。 - public の
ShogiArenaではpublic-ci.ymlがmake ciを実行します。 - public 側ではさらに、
public-docs.ymlが docs build と GitHub Pages deploy を、public-release.ymlが tag push (v*) を契機に GitHub Release と PyPI publish を担当します。 typing-audit-ciはagent-docs/の baseline に依存するため、develop 側 CI のみで実行します。
public への export は補助スクリプトで行えます。
scripts\export_public_snapshot.ps1 -NotesFile release-notes\v0.8.0.txt v0.8.0
git push public HEAD:main
このスクリプトは develop/main の内容を public snapshot に重ねます。
その際、agent-docs/ や AGENTS.md などの dev-only ファイル、dist/ や site/ のようなローカル生成物、public 側で使わない develop-ci.yml を除外します。
実装正本と facade の配置
実装正本は _core 以下にあります。
src/shogiarena/_core/contextssrc/shogiarena/_core/platformsrc/shogiarena/_core/interfacessrc/shogiarena/_core/shared/kernel
利用者向け facade は src/shogiarena 直下に置きます。
src/shogiarena/engine.pysrc/shogiarena/tournament.pysrc/shogiarena/cli.pysrc/shogiarena/composition.py
変更時の基本方針
- 公開 API の説明では
shogiarena.engineとshogiarena.tournamentを優先する _coreの deep import は contributor の実装用途に限定する- wiring は composition root に閉じ込める
- 編集は
apply_patchベースで行う - 破壊的変更を避けるための互換レイヤは原則作らない
最後の方針は、このリポジトリがまだ破壊的変更を許容していることによります。 互換レイヤを積み増すよりも、現在の正本がどこかを明確に保つほうを優先します。
テスト例
public API のテスト
import shogiarena.engine
import shogiarena.tournament
def test_public_engine_exports() -> None:
exported = set(shogiarena.engine.__all__)
assert "create_engine" in exported
assert "UsiEngineSession" in exported
# 内部の具象実装は公開面に出さない
assert "AsyncUsiEngine" not in exported
internal service のユニットテスト
from shogiarena._core.shared.kernel.statistics.btd_rating import BTDEstimator
def test_btd_estimation_runs() -> None:
estimator = BTDEstimator()
result = estimator.estimate(
games=[],
engine_names=["engine-a", "engine-b"],
)
assert result.anchor in {"engine-a", "engine-b"}
非同期 engine テスト
import pytest
from shogiarena.engine import UsiThinkRequest, create_engine_from_mapping
@pytest.mark.asyncio
async def test_engine_lifecycle() -> None:
async with await create_engine_from_mapping(
{
"name": "mock",
"engine_path": "path/to/your/engine",
"options": {},
}
) as engine:
result = await engine.think(
sfen="startpos",
request=UsiThinkRequest(movetime=100),
)
assert result.bestmove is not None
コミット
Conventional Commits を使います。
例:
refactor: move internals under _coredocs: align public api docs with facadestest: add public surface regression coverage
レビュー観点
特に次を見ます。
- 公開 API と internal API の境界が崩れていないか
_coreへの移動で import 方向が壊れていないか- facade が wiring を持ち込みすぎていないか
- docs が public surface と一致しているか