【EC-CUBE 4】特定のカテゴリー商品のみを取得・表示する方法

この記事では、特定の「カテゴリ」に属する商品のみをデータベースから検索し、一覧表示する方法を紹介します。デフォルトでカテゴリー別のページは用意されていますが、それとは別に特集ページを作りたいときなどに活用してみてください!

【動作環境】
EC CUBEのバージョン:4.3.0
サーバー:XServer

開発前にデバッグモードの設定をお薦めします

デバッグモードを設定しておくと、エラーが起きたときに詳細情報が表示されるようになります。
エラー箇所を探しやすくなるので、開発前に設定しておくのをオススメします。
デバッグモードの設定方法については 以下記事 で解説しています。

カスタマイズ後は、デバッグモードの解除を忘れないように。

目次

カテゴリー商品一覧ページの作成手順

全体の流れ
  1. カテゴリー商品一覧を表示する新規ページを作成。
  2. ①で作成した、新規ページのControllerファイルを修正。
  3. ①で作成した、新規ページのTwigファイルを修正。
  4. EC-CUBE管理画面にてキャッシュを削除。
STEP

新規ページの作成

以下記事の手順にて、まず新規ページを作成します。

STEP

Controllerの作成

STEP 1で作成したControllerファイルを以下の通り修正します。

<?php

namespace Customize\Controller;

use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Routing\Annotation\Route;
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
use Sensio\Bundle\FrameworkExtraBundle\Configuration\Template;
use Eccube\Controller\AbstractController;
use Eccube\Repository\ProductRepository;  // ProductRepositoryの使用を宣言

class SampleController extends AbstractController
{
    /**
     * ProductRepositoryのインスタンスを保持するプロパティ
     * @var ProductRepository
     */
    protected $productRepository;

    /**
     * コンストラクタでProductRepositoryのインスタンスを注入
     * @param ProductRepository $productRepository
     */
    public function __construct(ProductRepository $productRepository) {
        $this->productRepository = $productRepository;
    }

    /**
     * @Route("/sample", name="sample")
     * @Template("sample.twig")
     */
    public function index(Request $request)
    {
        // ID=1 のカテゴリーをもつ商品を抽出するクエリを作成(IDは適宜修正してください)
        $customQb = $this->productRepository->createQueryBuilder('p');

        $customQb
            ->innerJoin('p.ProductCategories', 'pc')
            ->innerJoin('pc.Category', 'c')
            ->andWhere('c.id = :Category')
            ->setParameter('Category', 1);

        // 公開商品のみ取得したい場合は以下を有効化
        // ->andWhere('p.Status = :status')
        // ->setParameter('status', 1);

        // 上記クエリを実行し、ID=1 のカテゴリーをもつ商品を $products に格納
        $products = $customQb->getQuery()->getResult();

        return [
            // Twigテンプレートに渡す変数「Products」に、$products のデータを設定
            'Products' => $products,
        ];
    }
}

このControllerによって、@Routeで指定したURLにアクセスしたときに、データベースから特定のカテゴリーに該当する商品データを引っ張ってくることができます。

上記コードでは、URL「ドメイン名/sample」にアクセスしたときに、ID=1のカテゴリーに属する商品データが取得されます。カテゴリーIDは、管理画面の商品管理 > カテゴリ管理で確認できます。ご自身の状況に合わせて、適宜修正してください。

なお、RepositoryやControllerの仕組みや使い方については、以下記事にて解説しています。

【発展】クエリ部分をリポジトリに移行する

再利用性やメンテナンス性の観点から、このようなデータベースに関するクエリはリポジトリで定義することが推奨されています。

クエリの移行方法は以下記事で紹介しているので、合わせて設定しておくのをお薦めします。

STEP

新規ページ(Twigテンプレート)の編集

管理画面のコンテンツ管理 > ページ管理から、Twigテンプレートを編集します。

なお、このテンプレートの大部分は、デフォルトで用意されている「商品一覧ページ」を参考にしています。

{% extends 'default_frame.twig' %}

{% block main %}
  <div class="ec-shelfRole">
      <ul class="ec-shelfGrid">
          {# Productsに格納されているデータを順に取り出し、Productに代入 #}
          {% for Product in Products %}
            <li class="ec-shelfGrid__item">
                <a href="{{ url('product_detail', {'id': Product.id}) }}">
                    {# 商品画像の表示 #}
                    <p class="ec-shelfGrid__item-image">
                        <img src="{{ asset(Product.main_list_image|no_image_product, 'save_image') }}" alt="{{ Product.name }}" loading="lazy">
                    </p>
                    {# 商品名の表示 #}
                    <p>{{ Product.name }}</p>
                    {# 価格の表示 #}
                    <p class="price02-default">
                        {% if Product.hasProductClass %}
                            {% if Product.getPrice02Min == Product.getPrice02Max %}
                                {{ Product.getPrice02IncTaxMin|price }}
                            {% else %}
                                {{ Product.getPrice02IncTaxMin|price }} ~ {{ Product.getPrice02IncTaxMax|price }}
                            {% endif %}
                        {% else %}
                            {{ Product.getPrice02IncTaxMin|price }}
                        {% endif %}
                    </p>
                </a>
            </li>
          {% endfor %}
      </ul>
  </div>

{% endblock %}

STEP 1で作成したControllerにより、Productsには$producs(ID=1のカテゴリーに該当する商品情報)が格納されています。その商品情報を、for文を用いて「Product」として一つずつ取り出し、

Product.main_list_image

商品のメイン画像

Product.name

商品名

Product.getPrice

商品の価格

というように表示しています。
商品データの他の値(商品IDなど)を表示させることも可能です。

なお、Twigテンプレートのfor文については、以下記事で解説しています。

STEP

キャッシュを削除

ここまでで準備完了です。
管理画面からキャッシュを削除して、ページにアクセスしてみましょう。

キャッシュ管理からキャッシュを削除できます。

問題がなければ、指定したIDのカテゴリーに該当する商品一覧が表示されているはずです。!

まとめ

以上、特定のカテゴリーに属する商品のみを表示する「カテゴリー商品一覧ページ」を作る方法を紹介しました。特集記事などの作成の際に、ぜひ利用してみてください。


よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!
目次