Включение данных сериализатора django rest с помощью шаблона-тега Django `json_script`

Я использую Django Camel Case для перехода от pythons snake_case в бэкенде к camelCase во фронтэнде, чтобы ключи данных соответствовали обычному синтаксису JavaScript.

Это отлично работает для вызовов AJAX, возвращающих JSON.

Однако часто я хочу вставить некоторый JSON в HTML-шаблон с помощью стандартной функции Django 'json_script`. Я не хочу использовать какой-либо другой JSON strinfier, потому что тогда он не будет безопасно экранирован.

Проблема в том, что когда я вставляю JSON в HTML, он не camelCased:

Пример

# --- models.py ---
from django.db import models

class Foo(models.Model):
    last_name = models.CharField(max_length=250, unique=True)


# --- serializers.py ---
from rest_framework import serializers

class FooSerializer(serializers.ModelSerializer):
    class Meta:
        model = Foo
        fields = ('id', 'last_name')


# --- views.py --- 
from django.views import generic
from . import models

class IndexView(generic.ListView):
    template_name = f"myapp/index.html"
    model = Foo

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        context['serializer'] = serializers.FooSerializer(self.object_list, many=True)
        return context

Затем в шаблоне:

{{ serializer.data|json_script:"FOO_DATA" }}
<script type="module">
    const foos = JSON.parse(document.getElementById('FOO_DATA').textContent);
    console.log(foos)
</script>

Но, к сожалению, это приведет к чему-то вроде:

[{ id: 1, last_name: 'Smith'}, { id: 2, last_name: 'Kent'}]

Но я требую, чтобы last_name был в верблюжьей оболочке:

[{ id: 1, lastName: 'Smith'}, { id: 2, lastName: 'Kent'}]

Как можно безопасно внедрить данные JSON и преобразовать их в camelCase?

В итоге я создал пользовательский фильтр шаблонов, не вижу более простого способа:

from django import template
from django.utils import html
from django.utils.safestring import mark_safe

register = template.Library()


@register.filter()
def camelize_json_script(data, element_id):
    """
    Based on: django.utils.html.json_script

    Escape all the HTML/XML special characters with their unicode escapes, so
    value is safe to be output anywhere except for inside a tag attribute. Wrap
    the escaped JSON in a script tag.
    """
    from djangorestframework_camel_case.render import CamelCaseJSONRenderer

    json_str = CamelCaseJSONRenderer().render(data).decode().translate(html._json_script_escapes)
    return html.format_html(
        '<script id="{}" type="application/json">{}</script>', element_id, mark_safe(json_str)
    )

Если вы хотите автоматически загрузить этот тег шаблона, вы можете сделать это как показано здесь.

Вернуться на верх