PS PrestaShop Anfänger

DSGVO-Kontolöschung — Vollständige Anleitung

Installieren, konfigurieren und verwenden Sie die DSGVO-konforme Kontolöschung mit E-Mail-Bestätigung, Anonymisierung unter Wahrung der Buchhaltungsaufbewahrungspflicht und Mailchimp-, Brevo- und Mailjet-Abmeldung für PrestaShop 8 und 9.

Aktualisiert Modulversion 1.0.2

Überblick

Das Modul DSGVO-Kontolöschung bietet Ihren Kunden eine Möglichkeit, ihr Recht auf Löschung (Artikel 17 DSGVO) direkt aus ihrem Kundenbereich auszuüben, ohne manuellen Eingriff Ihrerseits. Eine Anfrage löst eine Kaskade aus: Bestätigung per E-Mail mit kryptografischem Token, Anonymisierung oder Löschung des Kontos shopseitig, automatische Abmeldung von Mailchimp, Brevo und Mailjet sowie Schreiben eines Verarbeitungsnachweises in ein Audit-Protokoll.

Für wen? Jeder PrestaShop-8- oder -9-Händler, der personenbezogene Daten europäischer Bürger verarbeitet und die manuelle Bearbeitung von DSGVO-Löschanfragen vermeiden möchte. Das Modul wird mit Französisch, Englisch, Spanisch und Deutsch geliefert.

Installation

  1. Melden Sie sich im PrestaShop-Backoffice an.
  2. Gehen Sie zu Module → Module Manager, klicken Sie auf Modul hochladen und legen Sie die Datei dfaccountdelete-1.0.2.zip ab.
  3. Das Modul wird automatisch installiert und aktiviert. Klicken Sie auf Konfigurieren.

Die Installation erstellt zwei Tabellen: ps_dfad_log (DSGVO-Protokoll) und ps_dfad_token (E-Mail-Bestätigungstoken). Sie registriert das Modul am Hook displayCustomerAccount, der einen Block „Mein Konto löschen“ zum Kundenbereich hinzufügt.

Wenn Sie viele angepasste Templates haben, prüfen Sie nach der Installation, dass der Block „Mein Konto löschen“ im Bereich Mein Konto shopseitig erscheint. Der Hook displayCustomerAccount muss von Ihrem Theme unterstützt werden — das ist beim nativen Classic-Theme und den meisten kommerziellen Themes der Fall.

Allgemeine Konfiguration

Der Konfigurationsbildschirm ist in vier Bereiche unterteilt: Allgemeine Einstellungen, Mailchimp, Brevo, Mailjet. Jeder Bereich wird unabhängig gespeichert.

Löschmodus

Wählen Sie zwischen zwei Modi:

  • Anonymisieren (empfohlen): die personenbezogenen Daten des Kunden (Vorname, Nachname, E-Mail, Telefon, Adressen, Geburtsdatum) werden durch anonyme Werte ersetzt. Bestellungen bleiben intakt, um die Buchhaltungs-Aufbewahrungspflicht (10 Jahre in Frankreich gemäß Artikel L123-22 des Handelsgesetzbuchs) zu erfüllen.
  • Vollständig löschen, falls möglich: Das Konto wird vollständig gelöscht, wenn keine Bestellungen existieren. Wenn Bestellungen existieren, wechselt das Modul automatisch in den Anonymisierungsmodus, um die rechtliche Historie nicht zu zerstören.

Auch im Modus „Vollständig löschen“ können Sie kein Konto löschen, das Bestellungen aufgegeben hat. Dies ist eine französische und europäische gesetzliche Verpflichtung. Das Modul behandelt diesen Wechsel automatisch und protokolliert im DSGVO-Protokoll den tatsächlich angewandten Modus.

Pflicht-E-Mail-Bestätigung

Standardmäßig aktiviert (dringend empfohlen). Der Kunde muss auf einen per E-Mail erhaltenen Link klicken, um seine Anfrage zu validieren. Dies verhindert jede versehentliche Löschung oder durch Dritte, die Zugriff auf eine offene Sitzung haben.

Token-Gültigkeitsdauer

In Stunden. Standardmäßig 24 Stunden. Nach Ablauf dieser Dauer läuft der Link in der E-Mail ab und die Anfrage wird automatisch storniert.

Protokolle

Standardmäßig aktiviert. Das Modul schreibt jede Anfrage in ps_dfad_log nur mit pseudonymisierten Daten: SHA-256-Hash der E-Mail, SHA-256-Hash der IP, Kunden-ID, angewandter Modus, Status, kontaktierte Anbieter, User-Agent, Shop-ID, Zeitstempel. Keine personenbezogenen Daten werden im Klartext gespeichert.

Die Tabelle ps_dfad_log wird bei der Deinstallation des Moduls nicht gelöscht. Dies ist beabsichtigt: Sie dient als Verarbeitungsnachweis bei einer Prüfung durch die Datenschutzbehörde. Um sie manuell zu löschen, führen Sie nach der Deinstallation DROP TABLE ps_dfad_log; aus.

Benachrichtigte Administrator-E-Mail

Adresse, die bei jeder erfolgreichen Löschung eine Benachrichtigung erhält (nur E-Mail-Hash, niemals die E-Mail im Klartext). Standardmäßig die Shop-E-Mail.

Konfiguration der Newsletter-Anbieter

Das Modul unterstützt standardmäßig drei Newsletter-Plattformen. Jeder Anbieter ist standardmäßig deaktiviert. Aktivieren Sie nur die, die Sie verwenden.

Mailchimp

Füllen Sie aus:

  • API-Schlüssel: Format xxxxxxxxxxxx-us21. Das Suffix (-us21, -eu1, usw.) ist das Mailchimp-Datacenter. Das Modul erkennt es automatisch.
  • List ID (Audience ID): Kennung Ihrer Hauptaudience. Zu finden in Mailchimp unter Audience → Settings → Audience name and defaults.
  • Dauerhafte Löschung: standardmäßig aktiviert. Verwendet den Endpoint POST /lists/{list_id}/members/{hash}/actions/delete-permanent, der dem echten Recht auf Vergessenwerden gemäß DSGVO entspricht: Die E-Mail wird dauerhaft gelöscht und Mailchimp wird jedes zukünftige Opt-in mit dieser Adresse ablehnen. Wenn Sie eine einfache Archivierung bevorzugen (die E-Mail kann sich dann später wieder anmelden), deaktivieren Sie diese Option.

Klicken Sie auf Verbindung testen, um Ihre Konfiguration zu validieren. Wenn alles korrekt ist, sehen Sie den Namen Ihrer Audience.

Brevo (ehemals Sendinblue)

Füllen Sie aus:

  • API-Schlüssel v3: Format xkeysib-xxxxxx. Zu finden in Brevo unter Mein Konto → SMTP & API → API-Schlüssel.
  • List ID (optional): Wenn angegeben, wird der Kontakt nur aus dieser Liste entfernt. Wenn leer, wird der Kontakt vollständig gelöscht (empfohlen für DSGVO).

Verwendeter Endpoint: DELETE /v3/contacts/{email} für vollständige Löschung oder POST /v3/contacts/lists/{id}/contacts/remove für Listenentfernung.

Mailjet

Mailjet verwendet Basic-Authentifizierung mit zwei Schlüsseln. Füllen Sie aus:

  • API Key
  • API Secret
  • Contact List ID (optional): Wenn angegeben, wird nur von dieser Liste abgemeldet. Wenn leer, wird der Kontakt über den offiziellen DSGVO-Endpoint von Mailjet gelöscht.

Der Mailjet-Löschfluss erfolgt in zwei Schritten: Suche der Kontaktkennung über GET /v3/REST/contact/{email}, dann DELETE /v4/contacts/{id} am DSGVO-Endpoint. Das Modul verwaltet diese Mechanik automatisch.

Wenn eine Plattform während der Löschung 404 zurückgibt, betrachtet das Modul dies als Erfolg (der Kontakt existiert nicht mehr, Idempotenz). Sie werden keinen Fehler in den Protokollen sehen.

Anonymisierung oder Löschung: welche Wahl?

Die DSGVO schreibt das Recht auf Löschung vor, aber das französische Handelsgesetzbuch verlangt die Aufbewahrung von Buchhaltungsdokumenten für 10 Jahre. Diese beiden Verpflichtungen werden durch Anonymisierung in Einklang gebracht, die die von der CNIL (französische Datenschutzbehörde) empfohlene Position ist.

Anonymisierungsmodus

Das Modul ersetzt in ps_customer:

  • firstnameAnonymized
  • lastnameCustomer
  • emailanon-{id_customer}-{hash}@anonymized.local
  • passwd → zufälliger Hash (der Kunde kann sich nicht mehr anmelden)
  • birthday → NULL
  • note, website, ip_registration_newsletter → leer
  • active → 0, deleted → 1

Für die Adressen:

  • Nicht von Bestellungen verwendete Adressen werden vollständig gelöscht.
  • Von Bestellungen verwendete Adressen werden anonymisiert (firstname, lastname, address1, postcode, city, phone, usw. durch neutrale Werte ersetzt) und als deleted = 1 markiert.

Vollständiger Löschmodus

Wenn der Kunde keine Bestellungen aufgegeben hat: vollständige Löschung der Adressen, dann Aufruf von Customer::delete(). Andernfalls: automatischer Wechsel in den Anonymisierungsmodus. Keine Option erlaubt es, die Löschung eines Kontos mit Bestellungen zu erzwingen — dies ist aus rechtlichen Gründen beabsichtigt.

Vollständiger Anfrageablauf

  1. Der Kunde geht zu Mein Konto und klickt auf den Block „Mein Konto löschen“.
  2. Er gelangt auf eine Bestätigungsseite mit einem Warnhinweis, einem Feld „Passwort“ und einer Checkbox „Ich verstehe, dass diese Aktion unwiderruflich ist“.
  3. Er gibt sein Passwort ein und kreuzt das Kästchen an. Das Modul verifiziert das Passwort über die Klasse PrestaShop/Core/Crypto/Hashing.
  4. Wenn die E-Mail-Bestätigung aktiviert ist, generiert das Modul ein zufälliges 32-Byte-Token (random_bytes(32)), konvertiert es in 64-stelliges Hexadezimal, speichert seinen SHA-256-Hash in ps_dfad_token und sendet eine E-Mail, die das Token im Klartext in einer URL enthält.
  5. Der Kunde erhält die E-Mail und klickt auf den Link. Das Modul ruft das Token aus der URL ab, berechnet seinen SHA-256 und überprüft, ob es in der Tabelle existiert, nicht abgelaufen ist und nicht bereits verbraucht wurde.
  6. Das Token wird als verbraucht markiert (consumed_at = NOW()), um eine Wiederverwendung zu verhindern.
  7. Für jeden aktivierten Anbieter (Mailchimp, Brevo, Mailjet) ruft das Modul die Lösch-API auf und protokolliert das Ergebnis (HTTP-Code, Nachricht).
  8. Das Modul bereinigt die PrestaShop-Tabellen: ps_emailsubscription, ps_newsletter, ps_cart, ps_cart_product, ps_wishlist, ps_compare, ps_customer_thread, ps_customer_message, ps_guest.
  9. Je nach Modus und Vorhandensein von Bestellungen wird das Konto anonymisiert oder gelöscht.
  10. Eine Zeile wird in ps_dfad_log mit dem Status done, dem tatsächlich angewandten Modus und der Liste der Anbieter-Ergebnisse eingefügt.
  11. Eine Benachrichtigungs-E-Mail wird an den konfigurierten Administrator gesendet (nur E-Mail-Hash).
  12. Der Kunde wird abgemeldet und auf eine Bestätigungsseite umgeleitet.

DSGVO-Verarbeitungsprotokoll

Der Konfigurationsbildschirm zeigt die letzten 30 Anfragen mit:

  • Anfrage-ID
  • Gekürzter E-Mail-Hash (erste 12 Zeichen des SHA-256)
  • Angewandter Modus (anonymize / delete)
  • Status (awaiting_confirm, done)
  • Liste der Anbieter und ihres Rückgabecodes, zum Beispiel mailchimp:OK(200) | brevo:OK(204) | mailjet:OK(200)
  • UTC-Datum und -Uhrzeit

Die vollständige Tabelle enthält außerdem: SHA-256-Hash der IP, auf 250 Zeichen gekürzten User-Agent, Shop-ID, interne Notizen (Vorhandensein oder Nicht-Vorhandensein von Bestellungen).

Um das vollständige Protokoll im Falle einer Prüfung zu exportieren, können Sie die Datenbank direkt abfragen: SELECT * FROM ps_dfad_log ORDER BY created_at DESC;. Keine Daten im Klartext erscheinen jemals in diesem Protokoll.

Testen vor dem Live-Gang

Empfohlenes Verfahren vor der Aktivierung des Moduls in einem Produktiv-Shop:

  1. Testen Sie die Anbieterverbindungen: Klicken Sie im BO des Moduls für jede aktivierte Plattform auf Verbindung testen. Sie sollten eine grüne Nachricht mit dem Namen Ihrer Audience/Ihres Kontos sehen. Bei einem Fehler wird die exakte HTTP-Nachricht angezeigt, die von der API zurückgegeben wurde.
  2. Testen Sie den vollständigen Ablauf an einem Testkonto:
    • Erstellen Sie ein Kundenkonto mit einer echten E-Mail-Adresse, die Sie kontrollieren.
    • Abonnieren Sie es manuell für Ihren Mailchimp/Brevo/Mailjet-Newsletter oder über das Formular Ihres Shops.
    • Überprüfen Sie, ob es auf jeder Plattform erscheint.
    • Melden Sie sich mit diesem Konto shopseitig an und starten Sie das Löschverfahren.
    • Bestätigen Sie über die erhaltene E-Mail.
    • Überprüfen Sie in ps_customer, dass das Konto ordnungsgemäß anonymisiert ist.
    • Überprüfen Sie auf jeder Newsletter-Plattform, dass die E-Mail verschwunden ist.
    • Überprüfen Sie den Eintrag in ps_dfad_log.
  3. Testen Sie den Fall „Kunde mit Bestellung“: Erstellen Sie ein Konto, geben Sie eine Testbestellung auf (1€) und starten Sie dann die Löschung im Modus „Vollständig löschen“. Überprüfen Sie, ob das Modul ordnungsgemäß zur Anonymisierung gewechselt hat und ob die Bestellung intakt ist, aber mit einer anonymen Adresse.

Erweitern: einen neuen Anbieter hinzufügen

Die Architektur folgt einem Strategy-Pattern. Das Hinzufügen von Sendgrid, Mailerlite, HubSpot, ActiveCampaign oder einer anderen Plattform erfordert nur die Erstellung einer Klasse.

Erstellen Sie classes/Provider/SendgridProvider.php:

class DfAccountDelete_SendgridProvider extends DfAccountDelete_AbstractProvider
{
    public function getKey() { return 'sendgrid'; }

    public function isEnabled()
    {
        return (bool) Configuration::get('DFAD_SG_ENABLED')
            && Configuration::get('DFAD_SG_API_KEY');
    }

    public function deleteSubscriber($email)
    {
        $headers = ['Authorization: Bearer ' . Configuration::get('DFAD_SG_API_KEY')];
        $url = 'https://api.sendgrid.com/v3/marketing/contacts?emails=' . rawurlencode($email);
        $res = $this->http('DELETE', $url, $headers);
        return ['ok' => $res['ok'], 'status' => $res['status'], 'message' => $res['message']];
    }

    public function testConnection()
    {
        $headers = ['Authorization: Bearer ' . Configuration::get('DFAD_SG_API_KEY')];
        $res = $this->http('GET', 'https://api.sendgrid.com/v3/scopes', $headers);
        return ['ok' => $res['ok'], 'status' => $res['status'], 'message' => $res['message']];
    }
}

Referenzieren Sie die Klasse in DfAccountDeleteService::getProviders():

public function getProviders()
{
    return [
        new DfAccountDelete_MailchimpProvider(),
        new DfAccountDelete_BrevoProvider(),
        new DfAccountDelete_MailjetProvider(),
        new DfAccountDelete_SendgridProvider(), // neu
    ];
}

Und laden Sie die Klasse oben in dfaccountdelete.php mit einem require_once. Der Rest (BO-Konfigurationspanel, Test-Button, Integration in den Löschablauf) ist ähnlich zu den bestehenden Anbietern zu programmieren.

FAQ und Fehlerbehebung

Der Kunde sagt, er habe die Bestätigungs-E-Mail nicht erhalten

Überprüfen Sie: (1) Funktioniert die PrestaShop-SMTP-Konfiguration (versenden Sie andere transaktionale E-Mails wie Bestellbestätigungen?), (2) befindet sich die E-Mail nicht in seinem Spam, (3) wurde die Ablaufzeit nicht erreicht. Der Kunde kann das Verfahren von seinem Konto aus neu starten — das neue Token macht die vorherigen automatisch ungültig.

Eine Newsletter-Plattform gibt einen 401-Fehler zurück

Der API-Schlüssel ist ungültig oder abgelaufen. Erstellen Sie ihn auf der betreffenden Plattform neu und aktualisieren Sie ihn in der Modulkonfiguration. Verwenden Sie die Schaltfläche Verbindung testen, um sofort zu validieren.

Der SQL-Fehler „LIMIT 1 LIMIT 1″ tritt auf

Sie verwenden eine Version älter als 1.0.1. Aktualisieren Sie auf die neueste Version: Dieser Fehler wurde in 1.0.1 behoben.

Das Konto scheint nicht anonymisiert: Vorname/Nachname/E-Mail sind weiterhin sichtbar

Sie verwenden eine Version älter als 1.0.2. Die interne PrestaShop-Validierung in Validate::isCustomerName() lehnte den alten lastname-Wert ab, der das Zeichen # und Ziffern enthielt, was dazu führte, dass die Aktualisierung stillschweigend fehlschlug. Aktualisieren Sie auf 1.0.2: Das automatische Upgrade repariert auch Konten, die in früheren Versionen schlecht anonymisiert wurden.

Wie lösche ich das DSGVO-Protokoll bei der Deinstallation?

Die Tabelle ps_dfad_log wird bei der Deinstallation absichtlich beibehalten (Verarbeitungsnachweis). Um sie nach der Deinstallation manuell zu löschen: DROP TABLE ps_dfad_log; DROP TABLE ps_dfad_token;.

Ist das Modul mit meinem bestehenden DSGVO-Modul (gdpr, psgdpr) kompatibel?

Ja, beide Module können koexistieren. Das offizielle PrestaShop-Modul psgdpr wird hauptsächlich für den Datenexport und die Einwilligungsverwaltung verwendet; dfaccountdelete wird für die effektive Löschung von Konten mit Newsletter-Integration verwendet. Sie treten sich nicht auf die Zehen.

Kann der Kunde abbrechen, nachdem er auf den Button geklickt hat?

Ja, solange er nicht auf den Link in der Bestätigungs-E-Mail geklickt hat. Das Token läuft nach der konfigurierten Dauer (standardmäßig 24 Stunden) automatisch ab. Während dieses Zeitfensters bleibt das Konto voll aktiv. Wenn er nichts tut, wird die Anfrage storniert.

Wie füge ich den Löschblock anderswo als in „Mein Konto“ hinzu?

Sie können von jeder Seite (Footer, AGB-Seite, usw.) einen direkten Link zu {shop_url}/{lang}/module/dfaccountdelete/delete erstellen. Wenn der Besucher nicht angemeldet ist, wird er zur Anmeldeseite umgeleitet mit Rückkehr zur Löschseite nach der Authentifizierung.

Versionen und Changelog

1.0.2 — kritische Korrektur

  • Fix: anonymizeCustomer() verwendete Customer::update(), das durch Validate::isCustomerName() läuft. Diese Validierung verbietet Ziffern und das Zeichen # in firstname/lastname, was dazu führte, dass die Anonymisierung des ps_customer-Datensatzes stillschweigend fehlschlug. Durch ein direktes SQL-UPDATE ersetzt, das die Validierung umgeht.
  • Das Upgrade upgrade-1.0.2.php repariert rückwirkend Konten, die von früheren Versionen verarbeitet wurden und nicht anonymisiert blieben.

1.0.1 — Korrektur

  • Fix: tableExists() verwendete Db::getValue(), das automatisch LIMIT 1 anhängt. Die Abfrage SHOW TABLES LIKE 'xxx' LIMIT 1 ist ungültiges SQL in MariaDB. Durch executeS() ersetzt.

1.0.0 — Erstveröffentlichung

  • Kompatibilität PrestaShop 8.0 bis 9.x
  • Anonymisierungsmodus und vollständiger Löschmodus
  • E-Mail-Bestätigung mit SHA-256-Token
  • Mailchimp-, Brevo-, Mailjet-Integrationen
  • DSGVO-Verarbeitungsprotokoll
  • Oberfläche und E-Mail-Vorlagen in FR, EN, ES, DE
War diese Seite hilfreich?

Immer noch nicht weiter? Support kontaktieren