Відповіді:
Використовувати з:
{% with "shop/"|add:shop_name|add:"/base.html" as template %}
{% include template %}
{% endwith %}
shop_name
, тому це небезпечно.
shop_name
перш ніж передати його в контекст у представленні, get_context_data
переконайтеся, що він переведений за допомогою, ugettext
а не ugettext_lazy
.
Не використовуйте add
для рядків, ви повинні визначити такий тег:
Створіть файл: <appname>\templatetags\<appname>_extras.py
from django import template
register = template.Library()
@register.filter
def addstr(arg1, arg2):
"""concatenate arg1 & arg2"""
return str(arg1) + str(arg2)
а потім використовувати його, як говорить @Steven
{% load <appname>_extras %}
{% with "shop/"|addstr:shop_name|addstr:"/base.html" as template %}
{% include template %}
{% endwith %}
Причина уникнення add
:
Згідно з док
Цей фільтр спочатку спробує примусити обидва значення до цілих чисел ... Рядки, які можна примусити до цілих чисел, будуть підсумовані, а не зв'язані ...
Якщо обидві змінні будуть цілими, результат буде несподіваним.
add
» в поодинці просто не використовувати str()
в першу чергу , а не працювати на всіх для мене в той час як ваше рішення працює безвідмовно
{% load <appname>_extras %}
Зверніться до об'єднання рядків у шаблонах Джанго :
Для більш ранніх версій Django:
{{ "Mary had a little"|stringformat:"s lamb." }}
"У Мері було трохи ягняти".
Ще:
{{ "Mary had a little"|add:" lamb." }}
"У Мері було трохи ягняти".
Погляньте на add
фільтр .
Редагувати: Ви можете ланцюг фільтрів, щоб ви могли це зробити "shop/"|add:shop_name|add:"/base.html"
. Але це не буде працювати, оскільки оцінювати фільтри в аргументах залежить від тега шаблону, а розширення - ні.
Я думаю, ви не можете зробити це в шаблонах.
З документів:
Цей тег можна використовувати двома способами:
{% extends "base.html" %}
(з лапками) використовує буквальне значення "base.html" як ім'я батьківського шаблону для розширення.{% extends variable %}
використовує значення змінної. Якщо змінна оцінює рядок, Django використовуватиме цей рядок як ім'я батьківського шаблону. Якщо змінна визначається об'єктом Template, Django використовуватиме цей об'єкт як батьківський шаблон.Так здається, що ви не можете використовувати фільтр для маніпулювання аргументом. У вікні виклику вам потрібно або створити шаблон предка або створити змінну рядка з правильним шляхом та передати його контексту.
@ відповідь про помилку принципово правильна, для цього вам слід використовувати тег шаблону. Однак я віддаю перевагу трохи більш загальному тегу шаблону, який я можу використовувати для виконання будь-яких подібних операцій:
from django import template
register = template.Library()
@register.tag(name='captureas')
def do_captureas(parser, token):
"""
Capture content for re-use throughout a template.
particularly handy for use within social meta fields
that are virtually identical.
"""
try:
tag_name, args = token.contents.split(None, 1)
except ValueError:
raise template.TemplateSyntaxError("'captureas' node requires a variable name.")
nodelist = parser.parse(('endcaptureas',))
parser.delete_first_token()
return CaptureasNode(nodelist, args)
class CaptureasNode(template.Node):
def __init__(self, nodelist, varname):
self.nodelist = nodelist
self.varname = varname
def render(self, context):
output = self.nodelist.render(context)
context[self.varname] = output
return ''
а потім ви можете використовувати його так у вашому шаблоні:
{% captureas template %}shop/{{ shop_name }}/base.html{% endcaptureas %}
{% include template %}
Як зазначається в коментарі, цей тег шаблону особливо корисний для інформації, що повторюється в усьому шаблоні, але вимагає логіки та інших речей, які будуть накопичувати ваші шаблони, або у випадках, коли ви хочете повторно використовувати дані, передані між шаблонами через блоки:
{% captureas meta_title %}{% spaceless %}{% block meta_title %}
{% if self.title %}{{ self.title }}{% endif %}
{% endblock %}{% endspaceless %} - DEFAULT WEBSITE NAME
{% endcaptureas %}
і потім:
<title>{{ meta_title }}</title>
<meta property="og:title" content="{{ meta_title }}" />
<meta itemprop="name" content="{{ meta_title }}">
<meta name="twitter:title" content="{{ meta_title }}">
Кредит за тег захоплення належить тут: https://www.djangosnippets.org/snippets/545/
Мені здалося, що робота з {% with %}
тегом є досить складною. Натомість я створив наступний тег шаблону, який повинен працювати над рядками та цілими числами.
from django import template
register = template.Library()
@register.filter
def concat_string(value_1, value_2):
return str(value_1) + str(value_2)
Потім завантажте тег шаблону у свій шаблон у верхній частині, використовуючи наступне:
{% load concat_string %}
Потім ви можете використовувати його наступним чином:
<a href="{{ SOME_DETAIL_URL|concat_string:object.pk }}" target="_blank">123</a>
Я особисто вважав, що це набагато чистіше працювати.
Ви не можете робити маніпуляції зі змінними в шаблонах джанго. У вас є два варіанти: або написати власний тег шаблону, або зробити це з огляду,
extends
не має для цього можливості. Або покладіть весь шлях до шаблону в змінну контексту і скористайтеся цим, або скопіюйте тег шаблону та змініть його відповідним чином.
І декілька конкатенацій:
from django import template
register = template.Library()
@register.simple_tag
def concat_all(*args):
"""concatenate all args"""
return ''.join(map(str, args))
І в Шаблоні:
{% concat_all 'x' 'y' another_var as string_result %}
concatenated string: {{ string_result }}