# Notification Center for Shopware 6 — Installation, configuration and technical documentation

> Overview The DataFirefly Notification Center adds a notification bell to the Shopware 6 storefront header, right next to the cart. A red badge shows the number of unread messages (displayed…

- Page: <https://www.datafirefly.com/en/documentation/dff-notification-center-shopware/>
- Language: en
- Last updated: 2026-07-08
- Other languages: [fr](https://www.datafirefly.com/documentation/dff-notification-center-shopware/index.md), [de](https://www.datafirefly.com/de/documentation/dff-notification-center-shopware/index.md), [es](https://www.datafirefly.com/es/documentation/dff-notification-center-shopware/index.md), [it](https://www.datafirefly.com/it/documentation/dff-notification-center-shopware/index.md), [pl](https://www.datafirefly.com/pl/documentation/dff-notification-center-shopware/index.md), [nl](https://www.datafirefly.com/nl/documentation/dff-notification-center-shopware/index.md), [pt](https://www.datafirefly.com/pt/documentation/dff-notification-center-shopware/index.md)
- Index: <https://www.datafirefly.com/en/documentation/llms.txt>

## Overview

The DataFirefly Notification Center adds a **notification bell** to the Shopware 6 storefront header, right next to the cart. A red badge shows the number of unread messages (displayed as "9+" beyond nine) and a dropdown panel presents your announcements, new products and promo codes.

The plugin handles three notification types: manually written **announcements**, **product notifications** created automatically for every new product (image and link resolved in real time), and **promo codes** with a one-click "Copy" button. Every notification can be scheduled, targeted by customer group and sales channel, prioritised, and tracked with view and click KPIs.

One plugin, one ZIP, compatible with **Shopware 6.5, 6.6 and 6.7** — including the Vite-based administration of 6.7, shipped pre-compiled with no build step.

## Requirements

- Shopware 6.5, 6.6 or 6.7 (`shopware/core` ~6.5 || ~6.6 || ~6.7)
- Command-line access to clear the cache and install assets
- No external dependency, no third-party service

## Installation

1. In the administration, go to **Extensions → My extensions → Upload extension** and select the ZIP.
2. Install and then **activate** the plugin.
3. Clear the cache and install the assets:

```
bin/console plugin:refresh
bin/console plugin:install --activate DffNotificationCenter
bin/console assets:install
bin/console cache:clear
```

After installing or updating, also clear your browser cache (Ctrl+F5) on the administration page to reload the module.

### Shopware 6.7 (Vite administration)

The administration module ships **pre-compiled** with a Vite `entrypoints.json` file. It loads as-is on 6.5, 6.6 and 6.7 with no build step. After each update simply run:

```
bin/console assets:install
bin/console cache:clear
```

## Configuration

Go to **Extensions → My extensions → Notification Center → Configure**. Settings are scopable per sales channel.

### Notification bell

- **Enable the bell** (default: yes): shows or hides the bell in the storefront.
- **Maximum number of notifications shown** (default: 10): clamped between 1 and 50 server-side.
- **Background refresh interval** (default: 60 s): polling interval, `0` to disable.
- **Sound** (default: no): plays a sound on a new notification.
- **Animation** (default: yes): animates the bell when unread notifications exist.

### Automatic product notifications

- **Create a notification for each new product** (default: yes).
- **Only for active products** (default: yes).
- **Automatic expiry** (default: 30 days, `0` = never): beyond it, the product notification is no longer delivered.

### Automatic promo notifications

- **Create a notification when a promotion with a code is created** (default: **no**, must be enabled explicitly).

The promo notification is created as soon as an **active** promotion has a **global code**. By design, individual codes are never broadcast.

## Managing notifications in the administration

The management module lives under **Marketing → Notification Center**. There you create, schedule, target and prioritise your announcements, and review view/click KPIs.

Three types are available:

- **Announcement** (`manual`): free title, message, button label and link.
- **Product** (`product`): linked to a product; the cover image and the link to the product page are resolved in real time on each render — never a broken link.
- **Promo code** (`promo`): displays a code with a client-side "Copy" button.

### Scheduling, targeting and priority

- **Scheduling**: `validFrom` / `validUntil` dates; a notification outside its window is not delivered.
- **Customer-group targeting**: limits delivery to a given customer group (empty = all).
- **Sales-channel targeting**: limits to one channel (empty = all), useful for multi-store setups.
- **Priority**: integer; higher priorities are shown first, then sorted by creation date descending.

## Client-side behaviour

The bell is inserted into the header via a Twig extension (`sw_extends`). If your theme heavily customises the header, a JavaScript _fallback_ automatically inserts the bell next to the cart.

The panel fetches notifications through an AJAX call. The badge shows the unread count, with optional sound and animation and a configurable background refresh. The interface is accessible: ARIA attributes, keyboard navigation, and a bottom-sheet layout on mobile.

**Read state:** for logged-in customers it is stored server-side (`dff_notification_read` table) and therefore synced across devices. For guests it stays in the browser's `localStorage` — no personal data is collected.

## Technical architecture

The plugin follows Shopware conventions: entities declared through the Data Abstraction Layer (DAL), a storefront controller returning JSON, event subscribers and a SQL migration. No override — templates are extended via `sw_extends` and the code is 100% native.

### Entities and the Data Abstraction Layer

The main entity `dff_notification` (`NotificationDefinition`) carries the fields: `type`, `active`, `priority`, `validFrom`, `validUntil`, `customerGroupId`, `salesChannelId`, `productId` (+ `productVersionId`), `promotionId`, `promoCode`, `views` and `clicks`. The translatable fields `title`, `message`, `buttonLabel` and `linkUrl` are carried by the translation entity `dff_notification_translation`.

Associations: `ManyToOne` to `customer_group`, `sales_channel`, `product` and `promotion`; `OneToMany` to `dff_notification_read` (per-customer read state). Definitions are registered with the `shopware.entity.definition` tag and exposed to the API (`ApiAware`).

### Database schema

The `Migration1781049600NotificationCenter` migration creates three tables:

- `dff_notification`: the notification, with indexes on `active` and on `(product_id, product_version_id)`. Foreign keys to `customer_group` and `sales_channel` (`ON DELETE SET NULL`) and to `product` (`ON DELETE CASCADE`).
- `dff_notification_translation`: per-language translations (`title`, `message`, `button_label`, `link_url`).
- `dff_notification_read`: notification/customer pairs, with a unique index on `(dff_notification_id, customer_id)` to prevent duplicate reads.

### Storefront AJAX routes

Routes are declared in XML (`Resources/config/routes.xml`) to stay compatible from Shopware 6.5 to 6.7 (Symfony 6.x and 7.x). The controller extends `AbstractController` — not `StorefrontController` — because it only returns JSON and `setTwig()` was removed in 6.7.

- `GET /dff-nc/list` → `list()`: returns deliverable notifications and increments their views.
- `POST /dff-nc/read` → `markRead()`: marks as read server-side (logged-in customers); for guests the response reports `client` storage.
- `POST /dff-nc/click/{id}` → `click()`: increments the click counter.

### Delivery logic (list controller)

The DAL query filters notifications with `active = true`, within their validity window (`validFrom` ≤ now ≤ `validUntil`, null bounds allowed), matching the current sales channel (or null) and the current customer group (or null), sorted by priority then creation date descending. Linked products are then resolved dynamically (`cover.media` association): a product notification whose product is deleted or unavailable in the channel is silently hidden. Views of the notifications actually delivered are incremented in a single query.

### Automatic notifications (subscribers)

**ProductSubscriber** listens to `product.written`. On every product _insert_ on the _live_ version (variants with a `parentId` are skipped), and if the option is enabled, it creates a `product` notification — honouring the "active products only" filter, the configured lifetime (`validUntil`) and a per-product de-duplication check.

**PromotionSubscriber** listens to `promotion.written`. Because the administration first creates the promotion then sets its code and active flag through subsequent updates, it reacts to both _inserts_ and _updates_. A `promo` notification is created only if the promotion is **active** and has a **global code**, carrying over the promotion's `validFrom`/`validUntil` dates with a per-promotion de-duplication check.

### Internationalisation

Three languages ship for both storefront and administration: French, English and German (snippets `fr-FR`, `en-GB`, `de-DE`). Default titles and messages for product and promo notifications are generated via the translation service (`dffNc.*` keys).

## Privacy (GDPR)

The plugin collects no personal data. Guests' read state stays in their browser (`localStorage`); logged-in customers' state is stored server-side and tied to their account. View and click counters are aggregated at notification level, with no individual profiling.

## Uninstalling

On uninstall, the `dff_notification_read`, `dff_notification_translation` and `dff_notification` tables are dropped — **unless** the "keep user data" option is ticked, in which case they are left intact.

## Troubleshooting

- **The bell does not appear**: check that the bell is enabled in the configuration, re-run `assets:install` and `cache:clear`, then clear the browser cache. The JS fallback inserts it next to the cart if the theme overrides the header.
- **No product notification created**: the option must be enabled, the product must be a root product (not a variant) and, if the filter is active, marked active.
- **No promo notification created**: the option is disabled by default; the promotion must be active and have a global code (individual codes are not broadcast).
- **Administration module not loading on 6.7**: re-run `assets:install` then `cache:clear` and force a browser reload (Ctrl+F5).
