django-datatables-viewによるServer-side processingで、DataTable向けのクエリパラメータを追加する

django-datatables-viewによるServer-side processingで、DataTable向けのクエリパラメータを追加しようと考えた時に詰まったことがあったため、メモを残します。

 

目次

 

環境

なお、サンプルの見栄えを良くするため、Bootstrap 4.5.2 も使っています。

 

やりたいこと

例えば以下のようなDataTableがあるとします。

f:id:thinkAmi:20201020214702p:plain

 
この状態で、もしHTMLのhidden input値があれば、その条件に従ってDataTableを絞り込んで表示したいとします。

例えば、

<input type="hidden" id="limitation" value="yellow">

と指定されている時は

f:id:thinkAmi:20201020215039p:plain

と絞り込まれた状態で表示します。

 

対応

フロントエンド

Server-side Processingで、バックエンドに渡すクエリパラメータを追加したい場合、 ajax オプションに data を追加します。
ajax - DataTables option

$('#demo').DataTable({
  autoWidth: false,
  serverSide: true,
  processing: true,
  responsive: true,
  ajax: {
    url: '/args-app/data/',
    type: 'GET',
    // 追加で渡すクエリパラメータを指定
    data: getLimitation(),
  },
  columnDefs: [
    {targets: 0, data: 'id'},
    {targets: 1, data: 'name'},
    {targets: 2, data: 'color__name'},
  ]
});


function getLimitation() {
  const limitation = $('#limitation');
  return limitation.length ? {limitation: limitation.val()} : {};
}

 

バックエンド

フロントからのクエリパラメータは、 _querydict の中に含まれています。

今回はクエリパラメータを元に絞り込みを行いたいため、 filter_queryset メソッドをオーバーライドします。

class AppleArgsDataTableView(BaseDatatableView):
    model = Apple

    columns = [
        'id',
        'title',
        'color__name',
    ]

    def render_column(self, row, column):
        if column == 'color__name':
            return row.color.name

        return super().render_column(row, column)

    def filter_queryset(self, qs):
        qs = super().filter_queryset(qs)

        # 追加されたクエリパラメータによる絞り込み
        limitation = self._querydict.get('limitation')
        if limitation == 'yellow':
            qs = qs.filter(color__name='黄')

        return qs

 

以上より、HTMLのhidden input値を元に、DataTableを絞り込んで表示できるようになりました。

 

ソースコード

GitHubに上げました。 args_app が今回のアプリです。
https://github.com/thinkAmi-sandbox/django-datatables-view-sample