4Sellers Integration

4Sellers Integration

Original documentation (German version):

Overview

This integration connects the third-party platform Maileon to enable automated marketing email delivery.

The system primarily monitors database tables for changes using an activity-based mechanism.

 

Whenever a change is detected:

  • A Maileon event (JSON object) is generated

  • Temporarily stored

  • Then transmitted to Maileon

Requirements

The integration must fulfill the following:

  • Integration of Maileon for automated marketing email delivery

  • Monitoring of database changes via activity services

  • Creation and temporary storage of Maileon event payloads

  • Transmission of events to Maileon

  • Newsletter subscriptions:

    • Transferred from the shop system to Maileon via the Activity Service

  • Newsletter unsubscriptions:

    • Handled on the Maileon side

    • Transferred to the shop via webhooks

  • Shop frontend must also support:

    • Sending unsubscribe requests back to Maileon

Implementation

Tracking

Database

  • A data project was created for temporary storage of tracking events:

    • cust_ToolboxMaileon_MaileonTrackingEvents

  • Optional:

    • SQL Agent Job to detect canceled shop orders

 

Activity Extension

An Activity project was implemented to generate Maileon events:

 

Tracked events:

  • Abandoned cart

  • Product added to wishlist

  • Back-in-stock notification

  • Shipping confirmation

  • Order cancellation

  • Initial newsletter subscriber sync

 

Responsibilities:

  • Event generation

  • Event transmission

  • Cleanup of already processed records

 

Shop Extension

Handles specific shop-side logic via ControllerActionHook:

  • Customer reactivation

  • Reset of disappearance flag

 

Client (API Layer)

A dedicated client handles communication with the Maileon API.

 

Integrated endpoints:

  • Get transaction types

  • Create transaction types

  • Create transactions

  • Unsubscribe contacts

 

Endpoints used:

 

Important Design Decision

When monitoring data changes, the CreatedAt timestamp plays a critical role.

 

Example:

  • It does not make sense to send an abandoned cart email for a cart created long ago

 

Therefore:

  • Only relevant, recent data is processed

  • This ensures performance and relevance

 

Newsletter Subscription & Unsubscription

Database

A dedicated data project includes:

  • cust_ToolboxMaileon_MaileonEventQueue

    → Stores webhook events and unsubscribe actions

  • cust_ToolboxMaileon_SubscriptionCustomFields

    → Stores additional fields for enriching newsletter subscriptions

 

Activity Service

Responsible for:

  • Sending newsletter subscriptions to Maileon

  • Processing webhook events (unsubscribe)

  • Processing frontend unsubscribe requests

 

Shop Extension

  • Custom controller for webhook handling

  • Controller hooks for unsubscribe tracking

 

Client

Handles:

  • Sending unsubscribe requests to Maileon

 

Tracking Events

Abandoned Cart

The system periodically scans the ShoppingCarts table for entries where:

  • The ModifiedAt timestamp is older than the configured threshold

  • The threshold is defined in:

    cust_ToolboxMaileon.abandonedCartPeriod (in hours)

Logic:

  • Current time − configured period = cutoff timestamp

  • If ModifiedAt > cutoff → event is created

Result:

An AbandonedCart event is generated and sent to Maileon

 

Article to Wishlist

  • The WishlistItems table is scanned regularly

  • Only new entries are considered

Result:

A Maileon event is created when a product is added to a wishlist

 

Back in Stock

  • Uses the Availability Check system

  • Entries are validated using the AvailabilityCheck SDK

Result:

A BackInStock event is generated when availability conditions are met

 

Customer Disappearance

The system monitors inactivity based on the Customers table:

  • Uses the LastLogOn field

  • Threshold defined in:

    cust_ToolboxMaileon.customerDisappearancePeriod (in days)

Logic:

  • Current time − configured period = cutoff timestamp

  • If LastLogOn < cutoff → customer is considered inactive

Result:

A CustomerDisappearance event is generate.

 

Customer Reactivation

This is the inverse logic of CustomerDisappearance:

  • A previously inactive customer logs in again

Result:

A reactivation event is sent to Maileon

Additionally:

  • The CustomerDisappearance flag is reset on login

 

Order Canceled

  • The Orders table is scanned for:

    • Process = 2000 (canceled status)

Result:

A cancellation event is sent to Maileon

 

ERP-based Cancellation Tracking (Optional)

Cancellations from ERP (e.g., OfficeLine) can also be tracked.

 

Mechanism:

  • SQL logic checks ERP transaction tables

  • If cancellation is detected:

    • A flag is set in the shop order:

      cust_ToolboxMaileon_ErpCanceled = 1

 

Requirement:

  • SQL Agent Job must be created:

;WITH CanceledPositions AS ( SELECT [VorPosID] ,[Mandant] ,[PosType] ,[VorID] ,[Artikelnummer] ,[AuspraegungID] ,[GGBestellt] ,[GGGeliefert] ,[GGRetour] ,[GGBerechnet] ,[GGErfuellt] ,[Timestamp] FROM [OLReweAbf].[dbo].[KHKVKVorgaengePositionen] (NOLOCK) WHERE GGErfuellt = -1 AND GGBerechnet = 0 AND GGBestellt > 0 ), CanceledOrders AS ( SELECT Bel.VorID , Bel.Mandant , Bel.USER_ShopOrderId , Bel.USER_ShopId , CO.GGErfuellt , CO.GGBestellt , CO.GGGeliefert , CO.GGBerechnet , O.* FROM OLReweAbf.dbo.KHKVKBelege Bel (NOLOCK) INNER JOIN CanceledPositions CO ON CO.VorID = Bel.VorID AND CO.Mandant = Bel.Mandant INNER JOIN Shopsystem.dbo.Orders O (NOLOCK) ON O.OrderId = Bel.USER_ShopOrderId AND O.ShopId = Bel.USER_ShopId WHERE NOT Bel.USER_ShopOrderId IS NULL AND NOT Bel.USER_ShopId IS NULL ) UPDATE Shopsystem.dbo.Orders SET cust_ToolboxMaileon_ErpCanceled = 1 FROM Shopsystem.dbo.Orders O INNER JOIN CanceledOrders CO ON CO.OrderId = O.OrderId AND CO.ShopId = O.ShopId
  • Execution interval: configurable

  • Must be set up after extension installation

 

This enables cross-system cancellation tracking

 

Order Placed

  • Completed orders are detected from the Orders table

Result:

An OrderPlaced event is sent to Maileon

 

RSS Feeds

For full functionality, the following RSS feeds must be provided:

  • All products

  • New products

  • Top sellers

 

Requirements:

  • Must be accessible from the Maileon server

  • Recommended location:

    • Inside the shop system’s wwwroot directory

 

Best practice:

  • Use SMB share on the web server

  • Activity Service accesses feeds via UNC path

⚠️ Important:

  • The target path must be accessible from the Activity Service

 

Maintenance

Checkout

  • The newsletter checkbox must be displayed during checkout

Required setting:

Orders → defaultNewsletterCheckoutActive = true

 

Webhooks

Webhooks are used to sync unsubscribe actions from Maileon back to the shop.

Configuration in Maileon:

  • HTTP POST URL format:

    https://[sub].[shop].[tld]/MaileonWebhook/Unsubscribe

Required payload fields:

  • Email address

  • External ID

  • Contact ID

 

Enriching Newsletter Subscriptions

Maileon allows extending subscription data with custom fields.

Steps

  1. Create custom fields in Maileon

  2. Map fields in the database table:

cust_ToolboxMaileon_SubscriptionCustomFields

 

Available Standard Fields

The following fields are already supported (marked * are auto-mapped):

  • Email address (*)

  • Title (*)

  • First and last name (*)

  • Organization (*)

  • Street and house number (*)

  • ZIP and city (*)

  • State (*)

  • Region

  • Country (*)

  • Language (*)

  • Gender

  • Date of birth (*)

  • Name day

 

Mapping is based on:

  • Newsletter subscription data

  • Matching active customer (excluding guest users)

 

Creating Custom Fields in Maileon

Step 1

Navigate to:

Lists and Contacts → Contact Fields → Create New Field

 

Step 2

Define field details in Maileon UI

 

Step 3 – Mapping

Configure mapping in:

cust_ToolboxMaileon_SubscriptionCustomFields

Fields:

  • FieldId → new GUID

  • ShopId → shop identifier

  • FieldName → Maileon field name

  • ObjectName → data source:

    • Customer (if logged in)

    • NewsletterSubscriptio

  • PropertyName:

    • Standard property → use model property name

    • Standard extension → prefix with ext_

    • Custom extension → prefix with cust_

 

Step 4

Restart the Activity Service

  • Shop frontend is NOT affected

 

Settings

Group: 

cust_ToolboxMaileon

Setting

Default

Description

Setting

Default

Description

apiKey

API key for Maileon event transmission

customerDisappearancePeriod

4

Days until customer is considered inactive

abandonedCartPeriod

4

Hours until cart is considered abandoned

preferredLanguage

1

Language of Maileon events

cleanUpSucceededRetentionPeriod

8

Retention (hours) for successful events

cleanUpErrorRetentionDays

7

Retention (days) for failed events

rssAllArticlesLocation

Path to RSS feed (all products)

rssNewArticlesLocation

Path to RSS feed (new products)

rssTopSellerArticlesLocation

Path to RSS feed (top sellers)

newArticlesThresholdDays

40

Days until product is considered “new”

 

Recommendations

To avoid performance bottlenecks:

  • Keep Activity intervals as short as possible

  • Prevent large data backlogs

 

Otherwise:

  • Risk of timeouts

  • High SQL load