очень самоуверенный, так что этот ответ по сути ... является мнением.
в моем понимании: чем больше нестандартных функций / фильтров используется в шаблоне, тем хуже вы семантически,С одной стороны, тот, кто редактирует или создает шаблоны, должен знать об этих функциях / фильтрах, что, на мой взгляд, нежелательно.
Кроме того, как уже упоминалось в комментарии к вопросу в DarkBee, фильтры предназначены дляпреобразование данных, а не получение их.функция ветки была бы более подходящей, но мне она тоже не нравится по вышеуказанной причине (она также предоставляет все шаблоны для этой функции, если не приняты меры предосторожности, с другой стороны, ожидаетсясуществует во всех шаблонах).
С другой стороны, редактор / создатель шаблонов также должен знать, какие переменные могут существовать в текущем контексте.Таким образом, в конечном счете, требуется предварительное знание.
Я хочу предложить немного другой (и, по моему высокомерному, но скромному мнению, вариант лучше ) ...
Насколько я понимаю, это было былучше, если бы вы могли просто использовать
{% for photo in post.photos %}
{# display of photos #}
{% endfor %}
, потому что они семантически связаны с постом, и также имеет смысл предположить, что они также структурно связаны.Поскольку ваш вариант использования выглядит немного по-другому, возможно, это будет:
{% for photo in posts.photos %}
, который, конечно, имеет другую семантику и действительно представляет собой винты с массивом posts
, где photos
- один элемент.Тем не менее, представьте, что коллекция является объектом, который имеет дополнительные функции (я буду бессовестно расширять доктрину ArrayCollection
):
<?php
namespace App\Collection;
use Doctrine\Common\Collections\ArrayCollection;
use App\Service\PhotoService;
class PostCollection extends ArrayCollection {
public $photoService;
public function __construct(array $elements, PhotoService $photoService) {
parent::__construct($elements);
$this->photoService = $photoService;
}
public function getPhotos() {
return $this->photoService->getReadMorePhotos($this->toArray())
}
}
, и тогда она будет вызываться в вашем контроллере.:
$response = $this->render(
'/content/photos.html.twig',
array(
'posts' => new PostCollection($posts, $photoService),
'loadMoreUrl' => $url,
'limit' => $limit
)
);
и может быть использован, как написано выше.
Почему это работает?ArrayCollection
реализует несколько интерфейсов, среди которых есть ArrayAccess
, а также IteratorAggregate
(что расширяет Traversable
), который позволяет вам использовать его в цикле, и он будет предоставлять коллекцию, которую он дал в своем конструкторе (или который изменяется в методах модификации), если возникнет такая необходимость, вы всегда можете получить массив с помощью ArrayCollection::toArray
.
Зачем это?Чтобы получить чистый код.
Должен ли я это сделать?НетНо это отчасти из-за моей привычки реализовывать почти все отношения в базе данных, которые в сочетании с ORM дают мне это бесплатно.