alexandrebulete/ddd-sylius-bundle
composer require alexandrebulete/ddd-sylius-bundle
config/bundles.php:
AlexandreBulete\DddSyliusBundle\DddSyliusBundle::class => ['all' => true],
config/packages/sylius_resource.yaml:
sylius_resource:
mapping:
paths:
- '%kernel.project_dir%/src/*/Infrastructure/Sylius/Resource'
Create a PostMenuContributor in your bounded context (e.g., src/Post/Infrastructure/Symfony/Menu/PostMenuContributor.php):
use AlexandreBulete\DddSyliusBundle\Admin\Menu\MenuContributorInterface;
use Knp\Menu\ItemInterface;
use Symfony\Component\DependencyInjection\Attribute\AutoconfigureTag;
#[AutoconfigureTag('app.menu_contributor')]
final readonly class PostMenuContributor implements MenuContributorInterface
{
public function contribute(ItemInterface $menu): void
{
$menu
->addChild('posts', ['route' => 'app_admin_post_index'])
->setLabel('Posts')
->setLabelAttribute('icon', 'tabler:article');
}
}
The menu item will now appear in the Sylius Admin UI under the configured route.
Post, User) defines its own menu contributor.#[AutoconfigureTag('app.menu_contributor')] to auto-register them.src/{Context}/Infrastructure/Symfony/Menu/ for clarity.Grid class (e.g., PostGrid) in src/{Context}/Infrastructure/Sylius/Grid/.GridPageResolver to handle pagination:
$page = GridPageResolver::getCurrentPage($grid, $request->query->all());
$itemsPerPage = GridPageResolver::getItemsPerPage($grid, $request->query->all());
Sylius\Grid\GridInterface for custom grid logic.Resource class (e.g., PostResource) in src/{Context}/Infrastructure/Sylius/Resource/.@Sylius\Resource\Resource).use Sylius\ResourceBundle\Doctrine\ORM\EntityRepository;
use Sylius\ResourceBundle\Resource\ResourceInterface;
#[Sylius\Resource\Resource('post')]
class Post implements ResourceInterface
{
use Sylius\ResourceBundle\Doctrine\ORM\EntityTrait;
}
src/
├── Post/
│ ├── Domain/ # Core logic (entities, services)
│ ├── Infrastructure/
│ │ ├── Sylius/ # Sylius-specific integrations (Grid, Resource)
│ │ └── Symfony/ # Symfony-specific integrations (Menu, Controllers)
│ └── Application/ # Use cases, commands
Menu Contributor Tagging:
#[AutoconfigureTag('app.menu_contributor')] will prevent the menu item from appearing.Grid Pagination Issues:
maxPerPage is not updating, ensure you’re using GridPageResolver correctly. The bundle fixes this in 1.0.1 via RequestGrid decorator.pagerfanta.max_per_page is being overridden elsewhere.Resource Mapping Paths:
%kernel.project_dir%/src/*/Infrastructure/Sylius/Resource) must match your project structure. Misconfiguration will ignore custom resources.sylius_resource:
mapping:
paths:
- '%kernel.project_dir%/src/Post/Infrastructure/Sylius/Resource'
php bin/console cache:clear).knp_menu.menu).Grid class is properly bound to a repository and the entity is mapped in Doctrine.dd($grid->getQuery()->getResult()) to inspect raw data.MenuContributorInterface to add dynamic logic (e.g., role-based visibility):
public function contribute(ItemInterface $menu): void {
if ($this->security->isGranted('ROLE_ADMIN')) {
$menu->addChild('admin_posts', [...]);
}
}
Grid methods like configure() to add custom filters:
public function configure(): void {
$this->add('status', 'status', [/* ... */]);
}
prePersist) in your bounded context’s infrastructure:
use Sylius\Component\Resource\Event\ResourceEvent;
$dispatcher->addListener(
'sylius.resource.post.pre_persist',
fn(ResourceEvent $event) => $this->prePersistLogic($event->getSubject())
);
1.11 for resource-bundle and 1.13 for grid-bundle. Mismatches may cause errors.composer.json or pin the bundle version.tabler:article) rely on the active Sylius admin theme (e.g., Bootstrap). Test icons in your theme’s documentation.How can I help you explore Laravel packages today?