この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。
こんにちは。サービスグループの武田です。
PythonのテンプレートエンジンであるJinja、使ってますか?直接使ったことはなくてもAnsibleやFlaskを使ったことがあればお世話になっているはずです。さて、このエントリはJinjaで正規表現置換フィルターregex_replace
を使いたいという趣旨です。おそらく読者の中には「いやそれ使ったことあるよ?」という方もいるはずなのですが、それはAnsibleの話だと思われます。実際に「Jinja regex_replace」で検索するとヒットするのはほぼAnsibleの記事です(執筆時点)。
というわけで、素のJinjaでregex_replace
を使用するための手順を紹介します。
環境
次のような環境で検証しています。
$ sw_vers
ProductName: Mac OS X
ProductVersion: 10.15.7
BuildVersion: 19H15
$ python3 -V
Python 3.9.1
$ pipenv --version
pipenv, version 2020.11.15
なお、Jinjaのバージョンは2.11.3
でした。
やってみた
まずはプロジェクトを作成しJinjaをインストールします。
$ mkdir jinja2_regex_replace && cd $_
$ pipenv install jinja2
次に正規表現フィルターを使う簡単なコードを用意します。
main.py
from jinja2 import Environment
env = Environment()
text = "Hello, {{ name | regex_replace('s+', 'S') }}"
tpl = env.from_string(text)
msg = tpl.render({"name": "Classmethod"})
print(msg)
実行してみましょう。
$ pipenv run python main.py
jinja2.exceptions.TemplateAssertionError: no filter named 'regex_replace'
はい、想定どおりそんなフィルターは見つかりません。それでは自分で追加して使えるようにしてみましょう。コードを次のように修正します。
main.py
import re
from jinja2 import Environment
def regex_replace(s, pattern, replace):
return re.sub(pattern, replace, s)
env = Environment()
env.filters["regex_replace"] = regex_replace
text = "Hello, {{ name | regex_replace('s+', 'S') }}"
tpl = env.from_string(text)
msg = tpl.render({"name": "Classmethod"})
print(msg)
フィルターといっても結局はPythonの関数です。正規表現置換するための関数を自分で定義します(5-6行目)。そしてその関数をregex_replace
という名前のフィルターとして登録します(9行目)。やることはこれだけです。あとは他のビルトインフィルターと同じようにテンプレート内で使えます!
実行してみましょう。
$ pipenv run python main.py
Hello, ClaSmethod
バッチリですね!
まとめ
regex_replace
で検索するとAnsibleばかりヒットするので、素のJinjaで使う方法を検証してみました。