Как я могу использовать пользовательский тег Django из поля таблицы PostgreSQL? (для цитат) - PullRequest
0 голосов
/ 12 февраля 2020

Короче говоря, я пытаюсь вызвать пользовательский тег Django из поля базы данных PostgreSQL.

Я использую DetailView для загрузки информации из модели «Нарушение». Модель «Беспорядок» содержит свободное текстовое поле с именем 'diagnostic_criteria'. Я хотел бы иметь возможность ссылаться на цитаты, хранящиеся в PolymorphicModel 'Reference' с полем 'diagnostic_criteria', используя пользовательский тег (в форме {%cite 'reference_slug'%}). У меня есть пользовательский тег, работающий, когда он вызывается непосредственно из шаблона (disor_detail. html), но теги в поле базы данных (загруженные как {{disorder.diagnostic criteria}}) не обнаруживаются.

Этот код и снимок экрана ниже иллюстрируют проблема. Ссылка (обозначенная {% 'reference1' %} отображается корректно при вызове из шаблона, но завершается ошибкой при ее импорте из базы данных. См. Ниже снимок экрана.

#pages/templates/disorders/disorders_detail.html

{% extends 'base.html' %}
{% load citation_tags %}
{% block content %}

<h1>{{ disorder.disorder_name }}</h1>

    <p>Let's have a look at the evidence.{% cite 'reference1' %}</p>

<h2>Diagnostic criteria</h2>

    {{ disorder.diagnostic_criteria | safe }}

{% show_references reference_list %}

{% endblock content %}

Контексты disorder.diagnostic_criteria показано на следующем снимке экрана:

enter image description here


Снимок экрана со страницы (немного другой исходный код, но важные вещи такие же):

enter image description here

#Sample code from models.py

class Disorder(models.Model):
    disorder_name = models.CharField(
        max_length=255,
        primary_key=True,
    )
    diagnostic_criteria = models.TextField(
        blank=True,
        null=True,
    )

class Meta:
    managed = True
    db_table = 'Disorder'

def __str__(self):
    return f"{self.disorder_name}"

Пользовательский тег работает с помощью приложения под названием «цитирование», основанного на коде из https://github.com/will-hart/django-citations. Я изменил это отчасти потому, что оно не работало (не совместимо с более новыми версиями Django), а отчасти потому, что я хотел что-то немного другое.

#from citations/templatetags/citation_tags.py

from django import template
import re

from citations.models import Reference as R

register = template.Library()

class CiteNode(template.Node):

    def __init__(self, citation):
        self.citation = citation
        self.citations = [x.replace("\"", "").replace("'", "") for x in citation.split(" ")]

    def render(self, context):
        # create a new reference list if this is the first list of references
        if 'reference_list' not in context:
            context['reference_list'] = []

        ref_ids = []

        # get each reference

        for r in self.citations:
            try:
                ref = R.objects.get(slug=r)

            except R.DoesNotExist:
                raise template.TemplateSyntaxError("Unknown citation: %s" % r)

            if ref in context['reference_list']:

                # find the id of the item in the reference list
                num = context['reference_list'].index(ref) + 1

            else:
                context['reference_list'].append(ref)
                num = len(context['reference_list'])

            if not num in ref_ids:
                ref_ids.append(num)

        if not ref_ids:
            return "[?]"

        return "[" + ", ".join(["<a href='#fn_{0}'>{0}</a>".format(x) for x in sorted(ref_ids)]) + "]"

def do_cite(parser, token):
    """
    Turns a {{cite "reference_slug"}} into a
    """

    # This version uses a regular expression to parse tag contents.
    try:
        # Splitting by None == splitting by spaces.
        tag_name, citations = token.contents.split(None, 1)
    except ValueError:
        raise template.TemplateSyntaxError("%r tag requires arguments" % token.contents.split()[0])
    if not (citations[0] == citations[-1] and citations[0] in ('"', "'")):
        raise template.TemplateSyntaxError("%r tag's argument should be in quotes" % tag_name)
    return CiteNode(citations)

@register.inclusion_tag("reference_list.html")

def show_references(reference_list):
    return {'references': reference_list}

@register.inclusion_tag("reference_list.html")

def show_all_references():
    refs = R.objects.all()
    return {'references': refs}

@register.filter

def startswith(value,arg):
    return str(value).startswith(str(arg))

register.tag('cite', do_cite)

Файл, содержащий модели цитирования, имеет вид следующим образом: # citations / models.py

from django.db import models
from polymorphic.models import PolymorphicModel

# Create your models here.

class Reference(PolymorphicModel):
    title = models.CharField(max_length=255, primary_key=True)
    slug = models.CharField(max_length=128, unique=True)
    url = models.URLField()

    class Meta:
        managed = True
        verbose_name_plural = "Evidence"

    def __str__(self):
        return f"{self.title}"

class Article(Reference):
    journal = models.CharField(max_length=255)

    class Meta:
        managed = True

    def build_citation(self):
        return f"{self.title}, {self.journal}, ({self.slug})"

Мне удалось запустить html код из полей в моделях ранее с помощью тега {{disorder.diagnostic_criteria | safe }}, но это неудивительно, как это было немного яма ttempt.

Я не вижу примеров вызова пользовательских тегов из моделей в документации Django или в сети, что вызывает сожаление. Я занимаюсь медициной, а не программированием, поэтому я был бы очень признателен за любые советы относительно того, возможно ли это, и если нет, то есть ли альтернативная стратегия, которую я мог бы использовать?

Спасибо за ваше время!

...