Flask Paginateでページネーション情報を日本語化する

# 概要

Flaskでページネーションを実現する方法として[Flask-Paginate](https://pythonhosted.org/Flask-paginate/)を使う方法があります。とても便利なのですが、デフォルトだと英語対応なので、日本語化する手順を紹介します。ドキュメントを読んでもわからなかったため、ソースコードを読みました。

一応、Flask-Paginateのミニマムな使用例にもなっています。
記事では部分的なコードしか書いていないので、全体を把握したかったり、手元で実行したい場合は、GitHubに置いてあります。

https://github.com/dorapon2000/dorapon2000-blog/tree/main/japanese_flask_paginate



# 検証環境

- Python 3.8.12
- Flask 2.0.2
- Flask Paginate 2021.10.29
- Bootstrap 5.0.0 と 4.3.1

# 解決したい問題

```python:app.py
from flask import Flask, render_template, request
from flask_paginate import Pagination, get_page_parameter
app = Flask(__name__)

@app.route('/')
def index():
    page = request.args.get(get_page_parameter(), type=int, default=1)
    limit = 5

    # DBアクセスのつもり
    users = search_users(page=page, limit=limit)
    user_count = count_users()

    pagination = Pagination(page=page, per_page=limit, total=user_count, record_name='users', css_framework='bootstrap5')

    return render_template('index.html', users=users, pagination=pagination)
```


```jinja:templates/index.html
    {{ pagination.info }}
    <table class="table">
      {% for user in users %}
        <tr>
          <td>{{ user }}</td>
        </tr>
      {% endfor %}
    </table>
    {{ pagination.links }}
```

![スクリーンショット 2021-11-15 2.53.59.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32402/132a1336-95c2-3788-4bef-a34faf916189.png)

[info](https://pythonhosted.org/Flask-paginate/#flask_paginate.Pagination.info)プロパティで表示できるページの情報`displaying 1 - 5 users in total 103`を日本語にしたいです。しかし、infoはメソッドではないので、引数で表示形式を変えるなどができません。

infoのバリエーションとしてもう一つ、`search=True`とすると検索結果風にもできます。これは謎ですが、`total`と`found`は両方指定する必要があります。

```python:app.py
pagination = Pagination(page=page, per_page=limit, search=True, total=user_count, found=user_count, record_name='users', css_framework='bootstrap5')
```

![スクリーンショット 2021-11-15 2.05.03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32402/7b1a818e-ba7e-fbce-ccd7-ccd75019cc69.png)

でも、やっぱり英語です。


# 日本語化

[display_msg]()にpythonのフォーマット文字列として直接HTMLを指定できます。

```python:app.py
    pagination = Pagination(
        page=page,
        per_page=limit,
        total=user_count,
        display_msg='<b>{total}</b> {record_name}中の <b>{start} - {end}</b> {record_name}',
        record_name='ユーザー',
        css_framework='bootstrap5',
    )
```

![スクリーンショット 2021-11-15 1.30.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32402/21122086-f467-ce1b-4b6d-49c42ccf607e.png)

そう！これがやりたかった。

ちなみに、デフォルトがどうなっているのかはFlask Paginateのソースコードを見るとわかります。

```python:__init__.py
DISPLAY_MSG = "displaying <b>{start} - {end}</b> {record_name} in \
total <b>{total}</b>"
```

[https://github.com/lixxu/flask-paginate/blob/v2021.10.29/flask_paginate/\_\_init\_\_.py#L185-L186](https://github.com/lixxu/flask-paginate/blob/v2021.10.29/flask_paginate/__init__.py#L185-L186)


## ページネーション部分の日本語化

ここまで触れませんでしたが、ページネーション部分は[Bootstrap 5](https://getbootstrap.jp/)を利用しています。Paginationの引数部分で`css_framework='bootstrap5'`として、htmlのheadタグにもBootstrap5へのリンクを埋め込んでいます。

問題は`css_framework='bootstrap4'`を指定したいときです。css_frameworkを指定しなかったときのデフォルトでもあります。

![スクリーンショット 2021-11-15 3.12.39.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32402/a681b778-c48b-28a3-f5f8-3f7139925705.png)

なんと！英語が現れました。これくらいであれば、日本語のページにあってもそこまで違和感ないですが、変更ができません。

解決策としては、`css_framework='bootstrap5'`を指定します（強引）。手元では、Bootstrap 4.3.1を実際に使っていてもちゃんと表示されました。


# 参考

https://github.com/lixxu/flask-paginate

https://www.ravness.com/posts/flaskpaginate