商品に紐づいたタグで商品一覧を絞り込みたいことありませんか?
example.com/products/list?category_id=2&tag_id=1みたいにtag_id=Xで商品一覧を絞り込めるようにしたいと思います。
1.app/Customize/Form/Extension/SearchProductTypeExtension.phpを作成
<?phpnamespace Customize\Form\Extension; use Eccube\Form\Type\SearchProductType;use Symfony\Component\Form\AbstractTypeExtension;use Symfony\Component\Form\Extension\Core\Type\HiddenType;use Symfony\Component\Form\FormBuilderInterface; class SearchProductTypeExtension extends AbstractTypeExtension{ /** * {@inheritdoc} */ public function buildForm(FormBuilderInterface $builder, array $options) { $builder->add('tag_id', HiddenType::class, []); } /** * {@inheritdoc} */ public function getExtendedType() { return SearchProductType::class; }}
2.app/Customize/Repository/TagIdSearchCustomizer.phpを作成
<?php namespace Customize\Repository; use Eccube\Doctrine\Query\QueryCustomizer;use Eccube\Repository\QueryKey;use Doctrine\ORM\QueryBuilder; /** * */class TagIdSearchCustomizer implements QueryCustomizer { /** * 検索のパラメータにtag_idを追加 */ public function customize(QueryBuilder $builder, $params, $queryKey) { if (!empty($params['tag_id']) && $params['tag_id']) { $builder->innerJoin('p.ProductTag', 'pt'); $builder->andWhere('pt = :tag_id'); $builder->setParameter('tag_id', $params['tag_id']); } } public function getQueryKey(): string { return QueryKey::PRODUCT_SEARCH; } }
上記の2ファイルを設置すれば商品一覧でtag_idを使えるようになります。
解説
SearchProductTypeExtensionについて
FormTypeのカスタマイズ
FormExtensionを使った拡張
Form Typeのカスタマイズは上記URLです。
src配下に存在しているSearchProductTypeが商品一覧のFormを定義しているファイルなんですね。それを拡張するということをgetExtendedTypeで指定していて、buildFormでtag_idをhiddenとして定義しています。
TagIdSearchCustomizer.phpについて
リポジトリのカスタマイズ
QueryBuilderの拡張 #2285, #2298
上記のページでRepositoryのカスタマイズ方法が記載されています。
ProductRepository::getQueryBuilderBySearchData()をカスタマイズするためにgetQueryKeyでreturn QueryKey::PRODUCT_SEARCH;としています。
tag_idというパラメータが存在した場合は、ProductTagとinner joinして結果を絞り込むようにしています。
コメント