Co-Authored-By: Claude Haiku 5.5 <noreply@anthropic.com>
26 KiB
Etappe 4 – Datenformate des Divi-Designsystems (Divi 5.2.1)
Stand 2026-09-28. Grundlage: Quelltext von Divi 5.2.1 und echte Daten, die über Divis eigene Speicherwege angelegt wurden (Seed-Skript tests/Integration/divi-seed-stage4-design.php, Fixtures tests/Fixtures/divi/stage4/). Erfüllt Spec §14 („Datenformate Designsystem nur aus Code abgeleitet“) und §15 („Format der Presets/Variablen an echten Daten verifizieren“).
Pfadangaben relativ zu wp-content/themes/Divi/. Abkürzung B5 = includes/builder-5/server/. Minifizierte Builder-Dateien liegen in includes/builder-5/visual-builder/build/; dort steht statt einer Zeile ein Suchbegriff.
Nachtrag Divi 5.15.1 (Etappe 4a, 2026-10-16)
Geprüft gegen Divi 5.15.1 (installiert, freigegeben):
GlobalPreset::save_data()hat den zweiten Parameter$skip_external_cache = false; das Plugin übergibt ihn nicht. Der Parameter wird mit einem internen Flag ($_skip_external_cache_nested) verodert und anET_Core_PageResource::remove_static_resources()weitergereicht.GlobalPresetController::sync_permission()verlangt jetzt zusätzlichedit_theme_options(5.2.1: nur Visual-Builder-Recht). Die Rechte in Spec §10 entsprechen damit Divi.- Der Sync nimmt Chunks an (
requestId,chunkIndex,totalChunks, Transientet_global_preset_chunks_<user>_<id>); das Plugin schickt nie Chunks. - Schrittfolge des Sync (ohne Chunks) unverändert:
prepare_data→get_data→validate_preset_count→ bei Löschaktionenget_deleted_preset_ids+remove_preset_from_legacy_option→save_data. Das Plugin wiederholt sie inDesignSystemWriter::savePresets()(Mirrorpreset-sync); diese Klasse existiert noch nicht (geplant für Etappe 4a). - Signaturen aus Plan Step 1 bestätigt (
prepare_data,validate_preset_count,save_data,get_deleted_preset_ids,remove_preset_from_legacy_option,can_current_user_use_visual_builder);option_name,get_data,get_preset_attrs,get_preset_attrs_mappingvorhanden. - Abweichungen bei der Formatprüfung am lebenden Bestand (Seed-Skript lief erfolgreich, Seite 170):
- Zeilennummern in den Abschnitten 1–8 beziehen sich auf 5.2.1 und stimmen nicht mehr (z. B.
save_datajetztGlobalPreset.php:548,sync_permissionjetztGlobalPresetController.php:465). - Gruppen-Preset-Einträge haben
groupNameundgroupId(wie in Abschnitt 3), aber keinrenderAttrsim Seed-Bestand;renderAttrsist optional. - Das Mapping (
Conversion::get_preset_attrs_mapping("divi/button")) liefertattrName,presetund bei BedarfsubName.presetist nicht immer eine Liste: gesehen wurden"meta","content"(String) und["html"](Array).
- Zeilennummern in den Abschnitten 1–8 beziehen sich auf 5.2.1 und stimmen nicht mehr (z. B.
- Keine weiteren Abweichungen zu §3, außer den oben genannten.
0. Grundlagen: wo Divi speichert
et_get_option()/et_update_option() (epanel/custom_functions.php:211, :272) haben drei Ziele:
- normale Theme-Option → Schlüssel im Array der Option
et_divi(autoload); - „Product Setting“ (letzter Parameter
true) → eigene Optionet_divi_<name>, autoload aus (:224,:288-292); et_delete_option()(:316) kennt keine Product Settings und löscht immer nur den Schlüssel inet_divi.
Folge: GlobalPreset::delete_data() (B5 Packages/GlobalData/GlobalPreset.php:149-158) ruft et_delete_option(option_name()) auf und entfernt die Option et_divi_builder_global_presets_d5 nicht – nur den statischen Cache. Für Etappe 4 nicht verwenden.
et_update_option() aktualisiert zusätzlich das globale $et_theme_options; direktes update_option('et_divi', …) lässt diesen Cache im selben Request veralten.
1. Globale Farben
Speicherort: et_divi['et_global_data']['global_colors'] (normale Theme-Option, kein Product Setting). Die fünf Customizer-Farben liegen nicht dort, sondern als et_divi['accent_color'], secondary_accent_color, header_color, font_color, link_color (Zuordnung GlobalData::$customizer_colors, B5 Packages/GlobalData/GlobalData.php:58-83).
Format eines Eintrags (Schlüssel = ID):
"gcid-q9swzy97df": {
"color": "#5b3a29",
"folder": "",
"label": "[Fixture] Holz dunkel",
"lastUpdated": "2026-09-27T22:21:39.000Z",
"status": "active",
"usedInPosts": []
}
- ID:
gcid-+ 10 Zeichen[0-9a-z](Builder:generateVariableId/generateNanoUuid,global-data.js, SucheS=(e,t)=>e||("colors"===t?`gcid-${_()}). Ältere Daten können UUIDs haben (gcid-79d0acb1-…, BeispieleGlobalData.php:700-770). Prüfung serverseitig nursubstr($id, 0, 5) === 'gcid-'(:597-603). status:active|inactive|temporary. Der Builder löscht nie: „Löschen“ setztstatus: inactive(global-data.js, Suchecase"DELETE_GLOBAL_COLOR").label/folderwerden gespeichert, obwohl der Konverter-Kommentar „not until D6“ sagt (:159-160); der Builder liestlabel(Suchelabel:t.label||"").lastUpdated: FormatY-m-d\TH:i:s.v\Z.- Relative Farbe (Farbe aus anderer Farbe):
colorenthält eine Referenz
$variable({"type":"color","value":{"name":"gcid-q9swzy97df","settings":{"lightness":30}}})$
mitsettingsaushue,saturation,lightness,opacity(GlobalData::transform_state_into_global_color_value,:181-206). CSS-Ausgabe:--gcid-989stx15zc: hsl(from var(--gcid-q9swzy97df) calc(h + 0) calc(s + 0) calc(l + 30));(FrontEnd/Module/Style.php:910-947überStyleLibrary/Utils/Utils.php:86-130). Abhängigkeiten werden rekursiv aufgelöst (GlobalData.php:220-310, Tiefe max. 10 in:1336ff).
Lesen: GlobalData::get_global_colors() (:333-354) liefert Customizer-Farben (neu erzeugt, folder: customizer, übersetztes Label, lastUpdated = jetzt, :370-398) vor den gespeicherten Farben; gleichnamige gespeicherte Customizer-IDs werden verworfen. Ergebnis wird statisch gecacht ($_cached_data), set_global_colors() setzt den Cache zurück, get_customizer_colors() hat einen eigenen static-Cache ohne Reset.
Schreiben: GlobalData::set_global_colors(array $data, $already_sanitized = false) (:650-691):
- ohne
$already_sanitized:sanitize_global_colors_data()(:585-616) – verwirft Einträge ohnecoloroder ohnegcid-, wendetsanitize_text_fieldauf jeden skalaren Wert an;usedInPostswird mitarray_mapbehandelt und muss ein Array sein (sonstTypeError). - Customizer-IDs im Payload →
et_update_option(<option_name>, color)und aus dem Payload entfernt (:664-674). $already_sanitized = falseersetzt alle gespeicherten Farben,truemischt (array_merge) mit den vorhandenen (:678-684).et_update_option('et_global_data', …), dannET_Core_PageResource::remove_static_resources('all', 'all', true)(:687-690).
Builder-Speicherweg: POST divi/v1/global-data/global-colors (VisualBuilder/REST/RESTRegistration.php:1001-1008) → Schema-Sanitize sanitize_global_colors_data (GlobalDataController.php:100-108) → set_global_colors($colors, true) (:71-78), also Mischen. Der Builder schickt dabei die komplette Farbliste einschließlich der fünf Customizer-Farben (global-data.js, Suche restRoute:"/divi/v1/global-data/global-colors"); Entfernen einer Farbe ist über diesen Weg nicht möglich.
Seiteneffekte:
- Customizer-Sync ist direkt eingebaut (Schritt 2); ein separater Hook existiert nur für Divi 4 (
includes/builder/functions.php:13205-13237,et_global_colors_saved, mit veralteten IDsgcid-header-color/gcid-font-color). usedInPostspflegt nur der Builder im Browser (UPDATE_GLOBAL_COLORS_USED_IN_POSTS); serverseitig wird es nie berechnet. Über PHP angelegte Farben behalten[].- Einmalige Migration Divi 4 → 5 (
maybe_convert_global_colors_data,:526-551) läuft beim Laden der Builder-Einstellungen (Framework/Settings/Settings.php:159-162).
Rechte: REST-Route nur current_user_can('edit_posts') (GlobalDataController.php:124-130); set_global_colors() selbst prüft nichts. Zusätzlich verlangt jede Divi-REST-Route den Nonce X-ET-Nonce für die Aktion /divi/v1/<route>--POST (Framework/Route/RESTRoute.php:98, Framework/Controllers/RESTController.php:158-178).
2. Globale Variablen
Speicherort: Product Setting et_divi_global_variables (eigene Option, autoload aus), gespeichert mit et_update_option('global_variables', $data, false, '', '', true) (GlobalData.php:1016).
Gespeichertes Format (PHP-Arrays):
{
"numbers": { "gvid-f6yq6mayfy": { "id": "gvid-f6yq6mayfy", "label": "[Fixture] Eckenradius", "value": "8px",
"order": "1", "status": "active", "lastUpdated": "…", "variableType": "numbers" } },
"strings": { … }, "images": { … }, "links": { … }, "fonts": { … }
}
- Typen: nur
numbers,strings,images,links,fonts(sanitize_global_variables_data,:804-850).colorswird beim Speichern verworfen – „Farb-Variablen“ im Variablen-Manager sind die globalen Farben aus Abschnitt 1. - ID:
gvid-+ 10 Zeichen[0-9a-z]; Pflicht:gvid--Präfix und nicht-leereslabel. - Das Feld
idim Eintrag ist nötig: die CSS-Ausgabe benutzt$value['id'], nicht den Schlüssel (FrontEnd/Module/Style.php:1002). - Sanitize:
valuebeistringszeichengetreu (wp_check_invalid_utf8+wp_kses_no_null), beilinksesc_url_raw, sonstsanitize_text_field– dadurch wirdorderzum String ("1").allowedActionswird verworfen. Der Builder speichert außerdemlastUpdatedundvariableTypemit (global-data.js, Suchecase"ADD_GLOBAL_VARIABLE"). status:active|archived. Builder-„Löschen“ setztarchivedundorder: null(Suchecase"DELETE_GLOBAL_VARIABLE"), echtes Entfernen nur ohne Label/Wert.numberserlaubt beliebige CSS-Ausdrücke (clamp(1.5rem, 4vw, 2.5rem)bleibt erhalten).
Lesen: GlobalData::get_global_variables() (:896-963) liefert ein Array, jede Gruppe als stdClass ((object) $items, :959-962), die Einträge darin als Arrays; ergänzt allowedActions und stellt die Customizer-Schriften --et_global_heading_font / --et_global_body_font (aus et_divi['heading_font']/['body_font'], Standard „Open Sans“, :93-104, :415-437) an den Anfang von fonts. Leere Gruppen sind leere stdClass (JSON {}). Eine beschädigte fonts-Gruppe wird still auf [] gesetzt (:925).
Schreiben: GlobalData::set_global_variables(array $data) (:1002-1020) ersetzt die komplette Option. Vorher also vollständig lesen, stdClass → Array wandeln, allowedActions und die beiden Customizer-Schriften herausnehmen (sonst landen sie in der Option), dann schreiben. import_global_variables() (:1087-1137) mischt, arbeitet aber mit stdClass-Gruppen und schreibt nur id/label/value/status.
Danach remove_static_resources('all', 'all', true).
Rechte: set_global_variables() prüft current_user_can('edit_theme_options') && et_pb_is_allowed('variables_manager') und kehrt sonst ohne Fehler zurück (:1003-1005). Die REST-Route prüft nur edit_posts (GlobalDataController.php:350-356) und meldet danach Erfolg mit den unveränderten Daten – ein stiller Fehlschlag. variables_manager ist ein Recht des Divi-Rollen-Editors (includes/builder/functions.php:9219-9222, Auswertung includes/builder/core.php:1128ff, Option et_pb_role_settings; ohne Eintrag gilt „an“).
Referenzen in Modulen und Presets: $variable({"type":"content","value":{"name":"gvid-…","settings":{}}})$ – für Zahlen/Schriften wird daraus var(--gvid-…) (StyleLibrary/Utils/Utils.php:86-130), für Strings/Links/Bilder der Wert beim Rendern (Dynamic Content, Packages/Module/Layout/Components/DynamicContent/DynamicContentGlobalVariableOptions.php). :root enthält nur numbers und fonts (Style.php:991-1030), Schriftwerte in Anführungszeichen. In post_content ist " innerhalb der Referenz als " kodiert (WordPress-Block-Serialisierung).
Schriften der Customizer-Seite schreibt der Builder separat: POST divi/v1/global-data/global-fonts → et_update_option('heading_font'|'body_font') + Cache leeren (GlobalDataController.php:166-190, Recht edit_posts).
3. Presets (Modul- und Optionsgruppen-Presets)
Speicherort: Product Setting et_divi_builder_global_presets_d5 (GlobalPreset::option_name() = builder_global_presets_d5, GlobalPreset.php:129), autoload aus. Divi-4-Presets: et_divi_builder_global_presets_ng (wird bei Bedarf importiert, Flag builder_is_legacy_presets_imported_to_d5).
Gespeichertes Format:
{
"module": {
"divi/button": { "default": "", "items": { "3gbmxlurey": { …Modul-Preset… } } },
"divi/divider": { "default": "g7kvfq5uh8", "items": { "g7kvfq5uh8": { … } } }
},
"group": {
"divi/font-body": { "default": "", "items": { "ja6o54jtlc": { …Gruppen-Preset… } } }
}
}
Modul-Preset-Eintrag: type: "module", id, name, moduleName, version (Builder-Version, hier "5.2.1"), created/updated (Millisekunden, Builder Date.now(); PHP-Hilfen _generate_new_preset nutzen time() in Sekunden, :1695-1707), attrs, optional styleAttrs, renderAttrs, groupPresets, priority, order.
Gruppen-Preset-Eintrag zusätzlich groupName (z. B. divi/font-body), groupId (Attributpfad im Quellmodul, z. B. content.decoration.bodyFont), moduleName (Quellmodul), optional primaryAttrName (nur über JS-Filter gesetzt, module-utils.js, Suche divi.optionGroupPresetPrimaryAttrNameResolver).
- IDs 10 Zeichen
[0-9a-z], ohne Präfix (BuildergenerateDefaultPresetName,global-data.js). Namen sind nicht eindeutig – der Builder zählt „Button 1, Button 2 …“. attrs= normale Modulattribute (Pfad wie im Block, z. B.button.decoration.background.desktop.value.color); Gruppen-Presets tragen die vollen Pfade des Quellmoduls und werden beim Anwenden auf andere Module umgerechnet (GlobalPresetItemGroup::_attrs_resolver,GlobalPresetItemGroup.php:245ff,GlobalPresetItemGroupAttrNameResolver).styleAttrs/renderAttrs: Teilmengen vonattrsfür CSS bzw. HTML/Skript. Serverseitig berechenbar mitConversion::get_preset_attrs($attrs, ['style'] | ['html','script'], Conversion::get_preset_attrs_mapping($moduleName))(B5Packages/Conversion/Conversion.php:2242,:2479; genutzt inconvert_preset,:2144-2145). Das Frontend benutztrenderAttrs/styleAttrsder Gruppen-Presets direkt (Packages/ModuleLibrary/ModuleRegistration.php:326-340).groupPresetsim Modul-Preset (verschachtelte Gruppen-Presets):{ "<groupId>": { "presetId": ["<id>"], "groupName": "divi/…" } }.defaultje Modul/Gruppe: ID des Standard-Presets oder"". Der Builder legt beim Öffnen des Preset-Managers leere Standard-Presets an (ADD_DEFAULT_MODULE_PRESET); ein Standard-Preset ohneattrserzeugt keine Klasse (get_module_preset_class_names,GlobalPreset.php:730-800).priorityfehlt meist und gilt dann als10(:676,:2078,:2761); das REST-Schema-Default10(GlobalPresetController.php,preset_type_properties) wird für verschachtelte Einträge nicht eingesetzt.
Verweise in Blöcken (post_content):
- Modul-Preset:
"modulePreset": ["3gbmxlurey"]– Array (Stapel); ein String ist Altformat und wird noch akzeptiert (normalize_preset_stack,:2627-2680)."","default","_initial"bedeuten „Standard-Preset“ (is_preset_id_as_default,:2691). FehltmodulePreset, gilt das Standard-Preset des Moduls. - Gruppen-Preset:
"groupPreset": { "module.decoration.spacing": { "presetId": ["apzj7e17ok"], "groupName": "divi/spacing" } }(get_selected_group_presets,:2021-2320; Überlagerung:2148). - Stapel: letztes Element gewinnt bei
get_selected_preset(:522-600);renderAttrswerden nachpriorityaufsteigend gemischt (:626-712). Verschachtelte und explizite Gruppen-Presets werden gestapelt, nicht ersetzt (:2148-2163). - Welche Gruppen ein Modul hat und wie sie heißen:
GlobalPreset::get_group_preset_default_attr(ModuleRegistration::get_module_settings($name))(:2332-2465), Namenslisteget_default_group_name(:2475-2511). Beispieldivi/text:content.decoration.bodyFont→divi/font-body,module.decoration.spacing→divi/spacing;divi/button:button.decoration.font→divi/font,button.decoration.button→divi/button.
CSS-Klassen im Frontend (GlobalPresetItemUtils::generate_preset_class_name, GlobalPresetItemUtils.php:43-78): preset--module--divi-button--3gbmxlurey, Standard-Preset preset--module--divi-divider--default, Gruppe preset--group--divi-blurb--divi-spacing--apzj7e17ok, verschachtelt preset--group--divi-text--divi-font-body--nested--ja6o54jtlc. Keine Klassen für divi/id-classes, divi/animation. Am Fixture geprüft (README in tests/Fixtures/divi/stage4/).
Schreiben: GlobalPreset::save_data(array $data) (:419-431) schreibt die komplette Option ungeprüft, leert Caches (remove_static_resources('all','all',true,'all',true) – Builder-CSS bleibt erhalten) und setzt self::$_data zurück. Sanitisierung gibt es nur in GlobalPreset::prepare_data() (:213-268): wandelt das REST-Format ({module: [{default, items: [ … ]}], group: …}, Listen statt ID-Schlüssel) ins Speicherformat, entfernt leere Attribut-Arrays und sanitisiert attrs/renderAttrs/styleAttrs mit SavingUtility::sanitize_block_attrs bzw. sanitize_group_attrs (VisualBuilder/Saving/SavingUtility.php:2153, :2296; ohne unfiltered_html wird gefiltert).
Builder-Speicherweg: POST divi/v1/global-data/global-preset/sync (RESTRegistration.php:1035-1045) → GlobalPresetController::sync (GlobalPresetController.php:45-187): optional in Blöcken (Transient 5 min), prepare_data, validate_preset_count (GlobalPreset.php:335-410: weniger Presets als gespeichert → Fehler 400 preset_count_decreased, außer actionType DELETE_MODULE_PRESET/DELETE_OPTION_GROUP_PRESET), bei Löschaktionen Bereinigung der Divi-4-Option (remove_preset_from_legacy_option), dann save_data. Der Builder schickt immer den vollständigen Bestand.
Rechte: sync_permission() = UserRole::can_current_user_use_visual_builder() (GlobalPresetController.php:460, Framework/UserRole/UserRole.php:38-70) – nur das Rollen-Recht „Visual Builder verwenden“ (Standard „an“), kein edit_theme_options. Dazu der Routen-Nonce wie in Abschnitt 1.
Preset-Historie: et_divi_builder_presets_history_meta ({index, size}) und et_divi_builder_presets_history_item_<n> gehören zu Divi 4 (includes/builder/feature/global-presets/History.php:4-10, Schreiben nur per AJAX et_builder_save_global_presets_history mit switch_themes, :75-139). Der Divi-5-Sync schreibt dort nichts; Rückgängig im Builder ist rein clientseitig. Lokal: {index: -1, size: 0}. Für Etappe 4 heißt das: eine Wiederherstellung gibt es nur über eigene Snapshots (Spec §7).
4. Theme-Optionen (et_divi)
Lokal ist keiner der Whitelist-Schlüssel gesetzt (Fixture et-divi-subset.json) – überall gelten Divi-Standards.
| Gruppe | Schlüssel in et_divi |
Schreibweg in Divi | Sanitize / Standard (Customizer, functions.php) |
|---|---|---|---|
| Schriften | heading_font, body_font, primary_nav_font, secondary_nav_font, all_buttons_font |
Customizer, global-fonts-REST (nur heading/body) |
et_sanitize_font_choices, Standard none (:2484, :2557, :3398, :3522, :4996) |
heading_font_weight, body_font_weight |
Customizer | et_sanitize_global_font_weight, 500 (:2509, :2582) |
|
| Größen | body_font_size (14), tablet_body_font_size, phone_body_font_size, body_header_size (30), tablet_header_font_size, phone_header_font_size |
Customizer | absint (:2208-2456); Tablet/Phone-Standard = nächstgrößerer Wert |
body_font_height (1.7), body_header_height (1) |
Customizer | et_sanitize_float_number (:2236, :2376) |
|
body_header_spacing (0), body_header_style ('') |
Customizer | et_sanitize_int_number, et_divi_global_font_style (:2348, :2404) |
|
| Layout | content_width (1080), gutter_width (3), section_padding (4), row_padding (2) |
Customizer | absint (:1824, :1852, :1927, :2011) |
| Farben | accent_color, secondary_accent_color, header_color, font_color, link_color |
Customizer und set_global_colors (Abschnitt 1) |
et_sanitize_alpha_color (:2534-2665) |
| Buttons | all_buttons_* (19 Schlüssel inkl. *_hover, z. B. all_buttons_bg_color, all_buttons_border_radius_hover) |
Customizer | je Feld (:4843ff) |
| Logo | divi_logo |
ePanel „Theme-Optionen“ | Typ upload, URL-String (options_divi.php:81) |
| SEO | divi_seo_home_*, divi_seo_single_*, divi_seo_index_* |
ePanel | Checkboxen 'on'/'false', Texte, Selects (options_divi.php:721-894; Speichern epanel/core_functions.php:868ff, Checkbox :969-970/:1049) |
- Customizer-Einstellungen sind
type => 'option'mit Schlüsselet_divi[<name>]undcapability => 'edit_theme_options'; Divi prüft zusätzlich das Rollen-Rechttheme_customizer(functions.php:1278). ePanel:edit_theme_options(epanel/core_functions.php:873) und Rollen-Rechttheme_options(functions.php:8834-8846). - Standardwerte weichen voneinander ab:
secondary_accent_colorhat im Customizer#8800FF(functions.php:2665), inGlobalData::$customizer_colorsund im Builder#2ea3f2(GlobalData.php:64-68,includes/builder/core.php:7293). Wer die Builder-Sicht (get_global_colors()) zurückschreibt, setzt die Customizer-Farbe damit fest auf#2ea3f2. Ebenso Schriften: Customizer-Standardnone, Builder-Sicht „Open Sans“. - Caches: nach Customizer-Speichern
remove_static_resources('all','all')(core/components/PageResource.php:944,:1139-1141) undet_pb_force_regenerate_templates(includes/builder/core.php:3771). Für eigene Schreibzugriffe gilt dasselbe.
5. Caches
ET_Core_PageResource::remove_static_resources($post_id, $owner, $force, $slug, $preserve_vb_files, $delete_files) (core/components/PageResource.php:1213-1232) läuft nur, wenn wp_doing_cron() oder et_core_security_check_passed('edit_posts') – ohne angemeldeten Benutzer (z. B. WP-CLI ohne --user) ist der Aufruf wirkungslos. Farben und Variablen rufen ('all','all',true), Presets ('all','all',true,'all',true) bereits selbst auf; der in Spec §7 vorgesehene Zusatzaufruf ist harmlos, aber redundant.
In-Request-Caches: GlobalData::$_cached_data (Reset bei set_*), GlobalPreset::$_data und $_normalized_preset_stack_cache (Reset in save_data/delete_data), static in get_customizer_colors()/get_customizer_fonts() und get_group_preset_default_attr() (kein Reset).
6. Rechte im Überblick
| Weg | Prüfung in Divi |
|---|---|
REST global-colors, global-fonts, global-variables |
edit_posts + Routen-Nonce |
GlobalData::set_global_variables() |
edit_theme_options und et_pb_is_allowed('variables_manager'), sonst stilles return |
GlobalData::set_global_colors(), GlobalPreset::save_data() |
keine |
REST global-preset/sync |
Rollen-Recht use_visual_builder + Routen-Nonce |
| Customizer | edit_theme_options + Rollen-Recht theme_customizer |
| ePanel | edit_theme_options + Rollen-Recht theme_options |
remove_static_resources |
edit_posts (oder Cron), sonst wirkungslos |
7. Abweichungen und Ergänzungen zu Spec §7
- „Variablen … über
GlobalData::set_global_variables“ – stimmt, aber die Funktion ersetzt die ganze Option, liefert keinen Fehler bei fehlenden Rechten und kennt keinen Typcolors. Das Tool muss vorher lesen,stdClass→ Array wandeln,allowedActionsund die zwei Customizer-Schriften entfernen und nach dem Schreiben per Lesen prüfen. - „globale Farben … inkl. der fünf Hauptfarben (über
set_global_colors)“ – die Hauptfarben landen inet_divi['accent_color']usw.; der zweite Parameter entscheidet zwischen Ersetzen (false) und Mischen (true). Für Änderungen einzelner Farben: Mischen; Löschen wie der Builder alsstatus: inactive. Hauptfarben nur schicken, wenn sie wirklich geändert werden sollen (Standardwert-Abweichung, Abschnitt 4). - „Presets … per Name“ – Namen sind nicht eindeutig; IDs sind 10-stellige Zeichenketten. Schreiben immer als vollständiger Bestand;
save_data()sanitisiert nicht → vorherprepare_data()(REST-Format) undvalidate_preset_count()wie der Controller verwenden.styleAttrs/renderAttrsmüssen mitgeschrieben werden (Frontend liest sie). - „Voraussetzung:
edit_theme_options; für Variablen zusätzlichvariables_manager“ – strenger als Divi selbst (Farben:edit_posts; Presets: nur Visual-Builder-Recht). Als bewusste Plugin-Entscheidung beibehalten; für Variablen ist die Doppelprüfung zwingend, weil Divi sonst still nichts tut. - „danach
remove_static_resources('all','all',true)“ – Divis Setter tun das schon; wirkungslos ohne angemeldeten Benutzer. Für Presets nutzt Divipreserve_vb_files = true. - Snapshots sind die einzige Wiederherstellung: Divi 5 führt für Farben, Variablen und Presets keine serverseitige Historie; die Option
et_divi_builder_presets_history_metagehört zu Divi 4. - Theme-Optionen:
divi_logounddivi_seo_*sind ePanel-Felder (andere Sanitize-Regeln, Checkbox-Werte'on'/'false'), keine Customizer-Einstellungen. Die übrigen Whitelist-Felder haben die Customizer-Sanitize-Callbacks aus Abschnitt 4 – diese sollten wiederverwendet werden. - Lesepfad des Plugins (
src/Integrations/Divi/Design/DesignSystem.php): Farb-„Variablen“ (variables['colors']) sind in 5.2.1 immer leer – globale Farben tragen Label und ID selbst.fonts()liefert die Builder-Sicht („Open Sans“), nicht den Customizer-Standardnone.
8. Stolpersteine (Kurzliste)
get_global_variables()liefertstdClassje Gruppe, gespeichert sind Arrays; leere Gruppe ={}im JSON.- Variableneinträge brauchen das Feld
id;orderwird zum String. usedInPostsmuss ein Array sein; wird nur vom Builder gepflegt.created/updatedin Millisekunden (Builder) vs. Sekunden (PHP-Hilfen).modulePresetist ein Array; Standard-Preset wirkt nur mitattrs.- Sync-Endpunkt verweigert kleinere Preset-Anzahl ohne
DELETE_*-actionType. GlobalPreset::delete_data()löscht die Product-Setting-Option nicht.- Divi-REST-Routen verlangen
X-ET-Noncepro Route; direkte PHP-Aufrufe umgehen Nonce, Schema und Rechteprüfung. secondary_accent_color: Customizer-Standard#8800FF, Builder-Standard#2ea3f2.