Narrativva SEM Integration for Seznam
Narrativva SEM Integration for Seznam
Description
Public beta: This plugin is in an early public testing phase. Test your setup on a staging site and verify event delivery and consent behavior before using it in production. Feedback and bug reports are welcome.
Need help with implementation? I can help you implement and configure the plugin on your website. Contact me by email.
This plugin installs Seznam Event Measurement sul.js on the frontend and sends selected server-side events directly from WordPress to Seznam SEM.
Supported frontend events:
- PageView
- ViewContent
- Search
- Contact from contact clicks or optional copied contact text
Supported server-side events:
- WooCommerce AddToCart, InitiateCheckout, AddPaymentInfo, and Purchase by default, with optional developer dataLayer Purchase mode
- Lead events (Contact Form 7, Elementor Forms, WPForms, dataLayer)
- WordPress/Woo CompleteRegistration
The plugin also captures sid, udid, and sznaiid, bridges Google Consent Mode v2 to SEM updateConsent, hashes S2S user data server-side, deduplicates duplicate form leads, and keeps S2S delivery logs with retry handling. Multi-premise routing keeps each Zboží.cz premise’s combined frontend SEM ID paired with its separate S2S SEM ID.
Optional features include Sklik Sandbox token support for S2S tests, frontend updateUserData for logged-in users after ad_user_data consent is granted, configurable WooCommerce product identifiers for matching Zboží.cz ITEM_ID, Action Scheduler support when available, and WP-Cron fallback for small sites.
Developers can connect any cookie banner/CMP through focused public hooks instead of relying on a plugin-specific cookie parser. Main integration points are nva_sem_s2s_disable_by_gdpr, nva_sem_s2s_consent_mode, nva_sem_s2s_hidden_identity_form_selectors, nva_sem_s2s_purchase_contents_item, nva_sem_s2s_phone_country_prefix, nva_sem_s2s_delivery_result, the nva_sem_s2s_track() PHP helper, and the browser object window.NvaSemS2SBridge.
Built-in CMP adapters are enabled for CookieYes and Cookiebot. CookieYes maps advertisement to ads consent, analytics/performance to analytics consent, and functional to functionality consent. Cookiebot maps marketing, statistics, and preferences to the matching Google Consent Mode v2 values. Developers can disable these adapters with nva_sem_s2s_disable_cookieyes_bridge and nva_sem_s2s_disable_cookiebot_bridge.
Plugin author: František Bujnovský, a web analyst and web developer who helps brands and businesses grow through web analytics, precise measurement, and development. Website: https://frantisekbujnovsky.com/. Email: bujnovskyf@gmail.com.
Privacy / External Services
This plugin depends on Seznam’s Event Measurement service. It loads an external script from Seznam (https://l.seznam.cz/sul.js) on the frontend to manage identity cookies and collect browser events. It also performs Server-to-Server (S2S) HTTP requests to Seznam (https://sem.seznam.cz/rtgconv) to dispatch conversion events. Data is sent when tracking is enabled and the relevant consent and event conditions are met.
Service documentation: https://napoveda.sklik.cz/merici-skripty/seznam-event-measurement/implementace-sem/server-to-server-s2s-mereni/
Seznam advertiser terms: https://napoveda.sklik.cz/pravidla/smluvni-podminky-pro-inzerenty/
Seznam privacy information: https://o-seznam.cz/pravni-informace/ochrana-udaju/
This is an independent open-source integration. It is not developed, endorsed, sponsored, or supported by Seznam.cz. Seznam and related marks belong to their respective owner.
To respect user privacy and comply with GDPR regulations, the plugin:
* Uses sid and udid only when available from sul.js, which requires ad_storage: granted.
* Captures sznaiid from the Sklik click URL parameter. It may temporarily store it in the plugin’s own first-party browser storage and sync it to WordPress/WooCommerce session/order metadata for later S2S attribution. Sklik SEM S2S documentation describes sznaiid as a click ID used for anonymous conversion modelling and states that it can be safely stored server-side without user consent.
* Sends s2s_headers with client IP address, User-Agent, and available Sec-CH-UA* Client Hints only when ad_storage consent is granted.
* Hashes personal user data (em, ph, fn, ln, etc.) using SHA-256 server-side before dispatching, and only sends it if ad_user_data consent is granted.
* Retains local S2S delivery logs for debugging. Payload previews are retained for diagnostics and are masked. Full payloads are temporarily stored while events are queued or retrying; after successful delivery or permanent failure they are cleared unless Debug Mode is enabled. Debug Mode caps log retention at 24 hours; turning Debug Mode off clears stored full payloads and debug-only log rows.
* Registers suggested Privacy Policy text in WordPress admin.
* Rate-limits the frontend Lead REST endpoint by source and client IP.
For Developers
Most sites do not need custom code. For custom integrations, the main extension points are:
nva_sem_s2s_track_lead( $args )for custom WordPress lead forms.nva_sem_s2s_track( $event_name, $event_data )for officially supported server-side SEM events, including valid non-WooCommerce Purchase payloads. Arbitrary event names are rejected.window.NvaSemS2SBridge.trackLead(args)for browser-triggered custom Lead tracking delivered through the plugin S2S endpoint.nva_sem_s2s_consent_modefor custom cookie banners or CMPs.window.NvaSemS2SBridge.setConsent(consentMode)for frontend consent changes from a custom banner.nva_sem_s2s_disable_by_gdprto halt all plugin tracking from site privacy logic.nva_sem_s2s_hidden_identity_form_selectorsto add exact custom forms that should receive sid/udid/sznaiid hidden fields.nva_sem_s2s_purchase_contents_itemto customize WooCommerce product ITEM_ID mapping.nva_sem_s2s_delivery_resultto react to S2S delivery results in custom monitoring or logging.nva_sem_s2s_premise_keyto select a configured Zboží.cz premise when URL matching is not enough.nva_sem_s2s_premise_routeto customize the final pair of frontend and S2S SEM IDs.
Hidden identity fields are intentionally limited to known form types by default. The broad all-forms mode is disabled in the admin UI for production safety.
Installation
- Upload the plugin folder to
/wp-content/plugins/. - Activate the plugin in WordPress admin.
- Open Narrativva SEM in the WordPress admin menu.
- Enable tracking and fill in the default Frontend SEM ID and S2S SEM ID.
- Configure the server-side event toggles and test the setup with the Sklik Sandbox.
- For multiple Zboží.cz premises, add one route per line under Zboží.cz premise routes:
key | domain or URL prefix | frontend SEM ID | S2S SEM ID.
Each route can match an exact domain, wildcard subdomain, path prefix, or full URL prefix. The global identifiers remain the fallback. WooCommerce snapshots the selected route into the order for stable delayed Purchase delivery.
Faq
No. Seznam requires sul.js even for S2S measurement. The plugin loads sul.js and uses it as the browser gateway for identity cookies and frontend events.
Frontend PageView, Contact Form 7, Elementor Forms, WPForms, dataLayer Lead tracking, and custom Lead helpers can work without WooCommerce. Built-in ViewContent, add-to-cart, checkout, payment, and WooCommerce order Purchase tracking require WooCommerce. Developers can enable dataLayer Purchase mode or send a valid custom Purchase S2S payload with nva_sem_s2s_track() when a non-WooCommerce flow provides the required event data.
Yes. Add a route for each premise with its own combined frontend SEM ID and separate S2S SEM ID. Routes can match domains or URL prefixes. Custom integrations can select a route with premise_key or the nva_sem_s2s_premise_key filter. Seznam’s documentation confirms that every connected Zboží.cz premise has its own combined frontend SEM ID and its own S2S SEM ID.
No. The public helpers accept only event names from Seznam’s official SEM event reference. ViewCart is not supported. To measure cart-page visitors, enable PageView and configure either a conversion or a retargeting list in Seznam based on PageView with a URL condition matching the cart page. Use AddToCart for additions and InitiateCheckout only when checkout begins.
No. SEM requires CZK. Non-CZK WooCommerce orders are skipped and logged.
Do not intentionally send the same conversion through both paths. Seznam’s current SEM documentation does not provide frontend/S2S deduplication. The plugin disables WooCommerce Purchase S2S when its dataLayer Purchase mode is enabled, but other custom integrations remain your responsibility.
Reviews
Changelog
0.6.2
- Added public-beta guidance to the plugin description and settings page.
- Added an invitation to contact the author for implementation and configuration help.
- Made diagnostic test notices translatable and kept consent help localized after AJAX refresh.
- Measurement behavior and existing settings are unchanged.
0.6.1
- Renamed the plugin and distribution slug to Narrativva SEM Integration for Seznam following WordPress.org review feedback.
- Added direct nonce verification before processing Elementor Atomic Form AJAX submissions.
- Removed translation files from the WordPress.org distribution package in favor of translate.wordpress.org.
0.6.0
- Added multi-premise Zboží.cz routing with separate frontend and S2S SEM IDs per premise.
- Restricted developer helpers to event names in Seznam’s official SEM reference; unsupported custom names such as ViewCart are rejected.
- Added a prominent frontend/S2S overlap warning and clarified that dataLayer Purchase is delivered through S2S; internal WooCommerce Purchase is disabled automatically, while external GTM or plugin tags must be disabled manually.
- Added exact-domain, wildcard-subdomain, path-prefix, and full-URL-prefix matchers with a global fallback route.
- Added
nva_sem_s2s_premise_key,nva_sem_s2s_premise_route, and explicitpremise_keysupport for custom integrations. - Snapshots the resolved premise IDs into WooCommerce orders so delayed and retried Purchase events keep the checkout destination.
0.5.0
- Prepared the plugin for WordPress.org review with a production release version, concise directory metadata, and complete external-service disclosures.
- Removed obsolete cart-page tracking and settings to match Seznam’s current official event reference.
- Documented single-premise scope and the need to avoid duplicate frontend and S2S conversions.
0.4.9-beta
- Removed low-level/internal developer hooks from runtime and documentation, keeping the supported public extension points focused on custom consent, custom leads, privacy stop, form selectors, product ITEM_ID mapping, phone prefix, and delivery result handling.
0.4.8-beta
- Reduced the Developers reference to practical public extension points and removed low-level/internal hooks from the admin UI and readme overview.
- Updated About feedback copy to invite bug reports and feature requests by email.
0.4.7-beta
- Fixed critical error caused by class_exists() calls triggering CookieYes plugin’s buggy autoloader.
0.4.6-beta
- Added a clearer About CTA linking to František Bujnovský’s other projects and a secondary email contact action.
0.4.5-beta
- Added a contextual Developers link from consent diagnostics when a custom consent filter is detected or when no known CMP is found and a custom cookie banner may need hook configuration.
0.4.4-beta
- Moved author and contact information out of Developers into a standalone About admin section.
- Added plugin purpose and current version to the About section.
0.4.3-beta
- Improved CMP detection in the admin UI by checking active CookieYes/Cookiebot WordPress plugins in addition to current request cookies.
- Split consent reporting into detected integration and current values source so admin requests without visitor cookies are no longer misleading.
- Redesigned the Developers integration reference into full-width rows with wrapping hook labels and endpoints.
- Updated author description.
0.4.2-beta
- Disabled the non-recommended “hidden identity fields on all forms” admin option for production safety. Default targeted form selectors remain active, and developers can extend them through
nva_sem_s2s_hidden_identity_form_selectors. - Added admin visibility for the currently detected consent source: Cookiebot, CookieYes, custom filter, or default fallback.
- Added stronger production warnings when Debug mode is enabled.
- Expanded the Developers tab with clearer hook groups and author contact details.
0.4.1-beta
- Fixed admin settings persistence for unchecked checkboxes by submitting explicit 0/1 values and sanitizing checkbox values instead of only checking field presence.
- Added dependent admin states so irrelevant fields are visually disabled when parent tracking toggles are off, including cart detection, Purchase product identifiers, Registration value, and Lead integrations.
0.4.0-beta
- Improved phone number hashing: numbers are now normalized to E.164 format before SHA-256 hashing for better match rate with Sklik (strips spaces, converts 00xx prefix to +xx, prefixes bare 9-digit Czech numbers with +420 by default). Country prefix overridable via
nva_sem_s2s_phone_country_prefixfilter. - Replaced UUID v4 event_id generation with UUID v7 (time-ordered). Monotonically increasing IDs improve server-side deduplication reliability as recommended by Sklik S2S documentation.
- Improved consent-mode handling for S2S payloads.
- Secured lead REST endpoint with WordPress nonce verification (
X-WP-Nonce) — previously the endpoint was publicly accessible. - Added
do_action( 'nva_sem_s2s_track_lead', $args )action hook (documented in README, was missing from previous release). - Fixed identity extraction from Elementor Forms and WPForms hidden fields for sites without WooCommerce session.
- Documented developer filters for phone normalization, hidden identity form selectors, and delivery-result integrations.
0.3.0-beta
- Added Sklik Sandbox token support for S2S test payloads.
- Added optional frontend
updateUserDatasupport for logged-in users after ad_user_data consent is granted. - Added configurable WooCommerce product identifier source for matching Zboží.cz ITEM_ID.
- Added Action Scheduler support with WP-Cron fallback for queued S2S delivery.
- Added lead REST endpoint rate limiting and WordPress Privacy Policy helper text.
- Added custom log table schema version upgrade routine.
- Added S2S Lead tracking support for Contact Form 7, Elementor Forms, and WPForms.
- Added dataLayer Bridge to intercept GA4-like lead events on frontend and send them via S2S.
- Added public JS helper
window.nvaSemS2s.trackLead(args)and PHP helpernva_sem_s2s_track_lead(args). - Added transient-based deduplication layer with customizable TTL window.
- Added POST REST endpoint
/wp-json/nva-sem-s2s/v1/leadfor custom lead tracking. - Repositioned plugin from WooCommerce-only to general WordPress S2S tracking.
- Replaced old settings UI fields with an expanded “Lead Tracking” settings section and enhanced diagnostics check.
0.2.0
- Security: REST identity endpoint now properly verifies wp_rest nonce (permission_callback).
- Added WooCommerce HPOS (custom order tables) compatibility declaration.
- Removed runtime Composer dependency for distribution builds and switched to explicit class loading (manual requires) so the release ZIP works without Composer.
- Added proper uninstall.php + logs table cleanup.
- Added PHPCS (WordPress Coding Standards), PHPStan, and PHPUnit (basic unit tests for Options, EventBuilder, SemClient).
- GitHub Actions CI workflow (lint, phpcs, phpstan, tests, build).
- Major i18n work: admin UI strings converted to English source strings (ready for translations).
- Removed code duplication (product_category_path centralized).
- Unified result message helper.
- Light modernization of frontend.js and many supporting improvements (.distignore, phpunit.xml.dist, etc.).
- Bumped minimum WordPress requirement to 6.5.
0.1.0
- Initial implementation.