Metadata-Version: 2.4
Name: kt-datatable-view
Version: 0.1.0
Summary: DRF generic list view for the KTDatatable (Metronic-style) server-side sort/search/filter/pagination protocol
Author: Jishnu Chandran
License: MIT
Project-URL: Homepage, https://github.com/jishnu-ramachandran/kt-datatable-view
Classifier: Framework :: Django
Classifier: Programming Language :: Python :: 3
Classifier: License :: OSI Approved :: MIT License
Classifier: Intended Audience :: Developers
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: Django>=4.2
Requires-Dist: djangorestframework>=3.14
Dynamic: license-file

# kt-datatable-view

DRF generic list view implementing the KTDatatable (Metronic-style) server-side
sort / search / filter / pagination protocol.

## Install

```bash
pip install kt-datatable-view
```

## Query-param contract

```
sort[field]=<field>&sort[sort]=asc|desc
query[generalSearch]=<text>          # search_query defaults to "generalSearch"
query[<filter_field>]=<value>        # one per entry in filter_fields
pagination[page]=<n>&pagination[perpage]=<n>
```

## Usage

```python
from kt_datatable_view import KTDatatableListView
from rest_framework.permissions import IsAuthenticated

from myapp.models import Article
from myapp.serializers import ArticleSerializer


class ArticleDataTableView(KTDatatableListView):
    permission_classes = [IsAuthenticated]
    queryset = Article.objects.all()
    serializer_class = ArticleSerializer
    field = "created_at"          # default sort field
    sort = "desc"                 # default sort direction
    search_fields = ["name", "code"]
    filter_fields = ["status", "category_id"]

    def get_queryset(self):
        self.queryset = Article.objects.select_related("category")
        return super().get_queryset()
```

Wire it up like any DRF view:

```python
# urls.py
path("articles/", ArticleDataTableView.as_view(), name="article-datatable"),
```

### Response shape

```json
{
  "meta": {
    "page": 1,
    "pages": 5,
    "perpage": 10,
    "total": 42,
    "sort": "desc",
    "field": "created_at",
    "query": ""
  },
  "data": [ ... ]
}
```

## Avoiding COUNT(*) on heavy querysets

`KTDatatableResultsPagination` uses `OptimizedCountPaginator`, which will use a
`queryset._count_queryset` attribute (if present) for the pagination count
instead of running `COUNT(*)` on the full annotated/joined queryset:

```python
def get_queryset(self):
    qs = Article.objects.select_related("category").annotate(...)
    qs._count_queryset = Article.objects.filter(...)  # cheap count-only queryset
    self.queryset = qs
    return super().get_queryset()
```

## License

MIT
