概要
Copierテンプレートで {{version}} のようなパスを記載し、Taskfile経由でコマンドを実行するとGo templateとして誤解釈され、エラーが発生する。
環境
- OS: WSL(Windows11, Ubuntu)
- lefthook: v1.13.6
- task: v3.45.4
- cspell: 11.6.2
発生したエラー
template: :1: function "version" not defined
再現条件
以下のような {{ }} を含むファイルパスが、Taskfileに引数として渡されると発生する。
# Copier
backend/tools/cli/templates/.../{{version}}/...
# Taskfile
task cspell -- <staged_files...>
再現手順
- Copierでテンプレートを作成するために
/.../{{version}}/...テンプレート名.py.jinjaを作成 - Taskfile経由で
task cspell -- <staged_files...>を実行する - 上記エラーが発生
原因
- Taskfileの CLI_ARGS は内部的に Go template として解釈される経路がある
- そのため、引数(=ファイルパス)に
{{version}}が含まれるとテンプレート評価が走ってしまう - →その結果、
{{version}}が「version関数呼び出し」として扱われ、versionが未定義のためエラーが発生する
解決策
{{ }}を[[ ]] に置き換えて、Taskfileに渡るファイルパスから{{ }}を排除する。
メモ: 実際の修正内容
- テンプレート呼び出し元pyのsrc_path(今回だとrouter_template)配下にcopier.ymlを作成
- 既存のtemplateの
{{ }}を[[ ]]に置換する
ルート
├─ tools
│ └─ cli
│ ├─ subcommands
│ │ └─ presentation.py # 呼び出し元
│ └─ templates
│ └─ router_template # src_path
│ ├─ copier.yml # ここにcopier.ymlを追加
│ └─ src/app/presentation/http/controller
│ └─ [[version]]
│ └─ [[controller_name]]
│ └─ router.py.jinja
└─ ...
# テンプレート呼び出し元
# tools/cli/subcommands/presentation.py
@app.command(help="Add a new route.")
def add_route(
controller: Annotated[
str, typer.Option(help="Controller name", callback=non_blank_validator)
],
version: Annotated[int, typer.Option(help="Version number")] = DEFAULT_VERSION,
):
typer.echo(f"Route added to version {version}.")
run_copy(
src_path="root_dir/backend/tools/cli/templates/router_template",
dst_path="root_dir/backend",
data={"controller_name": controller, "version": str(version)},
)
# 追加するyml
# tools/cli/templates/router_template/copier.yml
_envops:
variable_start_string: "[["
variable_end_string: "]]"
block_start_string: "[%"
block_end_string: "%]"
comment_start_string: "[#"
comment_end_string: "#]"
keep_trailing_newline: true
version:
type: int
choices:
- 0
- 1
controller_name:
type: str
補足
参考URL
- lefthook configuration
https://lefthook.dev/configuration/ - Copier documentation
https://copier.readthedocs.io/ - Jinja2 documentation
https://jinja.palletsprojects.com/