Project Introduction: an Own Team Page with a Category Filter, Module and Page Concept
Project Introduction: an Own Team Page with a Category Filter, Module and Page Concept
~7 Min. Lesezeit Zuletzt aktualisiert am August 9, 2026
From here on, across the rest of this block's chapters, we'll build one continuous example project: an own storefront page with a team overview that can be filtered live using category buttons - with no page reload at all. Each of the following chapters builds directly on the previous one, until by the end (chapter 22) we have a fully working, CSP-compliant page.
The page we're building
The goal is a page at the URL /team that displays every member of the fictional mironsoft team as a card grid - name, role, and category (e.g. "Development", "Design", "Support"). Category buttons above the grid let you filter the display live, with no page reload at all.
The module: Mironsoft_TeamPage
The page is built as a standalone module, Mironsoft_TeamPage, under app/code/Mironsoft/TeamPage/ - not as a theme override, since this is completely new functionality, not a customization of something that already exists (the rule of thumb from chapter 4: your own new modules bring their own templates along).
Target structure of the Mironsoft_TeamPage module (filled in across chapters 18-22)
app/code/Mironsoft/TeamPage/
├── registration.php
├── etc/
│ ├── module.xml
│ └── frontend/
│ └── routes.xml
├── Controller/
│ └── Index/
│ └── Index.php
├── ViewModel/
│ └── TeamMembers.php
└── view/
└── frontend/
├── layout/
│ └── team_index_index.xml
└── templates/
└── team/
└── index.phtmlRoute and URL
The route's front name is team, the controller is Index/Index - together that gives the URL /team (the default action index/index doesn't need to be spelled out in the URL). Chapter 18 covers routes.xml and the controller in detail.
The data: team members and categories
For this tutorial, a simple list hard-coded in the ViewModel is enough - no custom database schema, no repository pattern with real persistence. That keeps the focus on Hyvä-specific concepts (layout, ViewModel, template, Alpine, CSP) rather than data modeling. Planned categories: All, Development, Design, and Support.
Tipp: In a real project, you'd probably maintain team data through a dedicated CMS module, a database table, or a repository - the ViewModel would then internally inject a repository instead of containing the data directly. The structure of the templates and the Alpine logic in this tutorial stays unaffected by that, though: the ViewModel's outward-facing interface (getTeamMembers(), getCategories()) would be identical.
What's coming in the next chapters
- Chapter 18: create the Layout XML, route, and controller - the page becomes reachable at
/teamfor the first time (still without content). - Chapter 19: write the ViewModel with the team data.
- Chapter 20: style the template with Tailwind - a static card grid.
- Chapter 21: integrate Alpine filter logic - category buttons filter live.
- Chapter 22: register the inline script CSP-compliantly and test the entire page.