diff --git a/public/assets/js/api.js b/public/assets/js/api.js
index c7953ac..b8203b7 100644
--- a/public/assets/js/api.js
+++ b/public/assets/js/api.js
@@ -17,7 +17,7 @@ async function parseJsonSafe(res) {
}
}
-// ... oberer Teil unverändert ...
+// ...ss oberer Teil unverändert ...
/** zentraler Fetch-Wrapper: Credentials, no-store, 401→Login */
async function apiFetch(url, init = {}) {
diff --git a/public/assets/js/app.js b/public/assets/js/app.js
index 4caf1ac..f6f2dc5 100644
--- a/public/assets/js/app.js
+++ b/public/assets/js/app.js
@@ -18,7 +18,7 @@ async function ensureAuthenticated() {
window.location.href = '/login.php';
return false;
}
- // ✅ nur für eingeloggte Nutzer: UI freigeben
+ // ✅ nur für eingeloggte Nutzer: UI freigebensss
document.documentElement.classList.remove('auth-pending');
const appRoot = document.getElementById('app');
if (appRoot && appRoot.hasAttribute('hidden')) appRoot.removeAttribute('hidden');
diff --git a/public/assets/js/bridge/blocks-api.js b/public/assets/js/bridge/blocks-api.js
index 3f5c661..8d62221 100644
--- a/public/assets/js/bridge/blocks-api.js
+++ b/public/assets/js/bridge/blocks-api.js
@@ -303,11 +303,60 @@
setPreviewHtml(html) {
const safeHtml = html || this.renderError('Referenz lädt …');
- this.set('rawHtml', safeHtml);
+ const alreadyDecorated = /^\s*<[^>]+data-lib-ref="1"/i.test(safeHtml);
+ let decoratedHtml = safeHtml;
+ if (!alreadyDecorated) {
+ const kind = this.get('lib-kind') || '';
+ const id = this.get('lib-id') || '';
+ const attrs = [
+ 'data-lib-ref="1"',
+ kind ? `data-lib-kind="${kind}"` : '',
+ id ? `data-lib-id="${id}"` : '',
+ ].filter(Boolean).join(' ');
+ decoratedHtml = `
${safeHtml}
`;
+ }
+ this.set('rawHtml', decoratedHtml);
const comps = this.components();
if (comps && comps.length) comps.reset([]);
this.trigger('preview:update');
},
+ populatePlaceholder(el) {
+ if (!el || el.__libHydrated) return;
+ const kind = el.getAttribute('data-lib-kind');
+ const id = el.getAttribute('data-lib-id');
+ if (!kind || !id) return;
+ el.setAttribute('data-lib-ref', '1');
+ const applyHtml = (html) => {
+ if (typeof html === 'string' && html.length) {
+ el.innerHTML = html;
+ this.decoratePlaceholder(el, kind, id);
+ this.hydrateNestedReferences(el);
+ el.__libHydrated = true;
+ }
+ };
+ const cached = this.getCachedApiItem(kind, id);
+ if (cached && cached.html) {
+ applyHtml(cached.html);
+ }
+ this.fetchReference(kind, id).then((item) => {
+ if (item && item.html) applyHtml(item.html);
+ });
+ },
+
+ decoratePlaceholder(el, kind, id) {
+ el.setAttribute('data-lib-ref', '1');
+ if (kind) el.setAttribute('data-lib-kind', kind);
+ if (id) el.setAttribute('data-lib-id', id);
+ el.setAttribute('contenteditable', 'false');
+ el.style.pointerEvents = 'none';
+ el.style.userSelect = 'none';
+ },
+
+ hydrateNestedReferences(root) {
+ if (!root) return;
+ const placeholders = root.querySelectorAll('[data-lib-kind][data-lib-id]');
+ placeholders.forEach((node) => this.populatePlaceholder(node));
+ },
reloadComponentContent(opts = {}) {
const kind = this.get('lib-kind');
@@ -337,11 +386,11 @@
} else {
log(`RELOAD FEHLER: Inhalt ${kind}/${id} nicht gefunden.`, '#dc3545', 'error', true);
this.setPreviewHtml(
- this.renderError(`🛑 Fehler: Inhalt für ${kind}/${id} nicht gefunden.`)
- );
- }
- })
- .catch((error) => {
+ this.renderError(`🛑 Fehler: Inhalt für ${kind}/${id} nicht gefunden.`)
+ );
+ }
+ })
+ .catch((error) => {
log('RELOAD FETCH ERROR', error?.message || String(error), '#dc3545', 'error', true);
this.setPreviewHtml(this.renderError('🛑 Fehler beim Laden der Referenz.'));
});
@@ -383,6 +432,7 @@
wrap.style.pointerEvents = 'none';
wrap.style.userSelect = 'none';
this.el.appendChild(wrap);
+ this.model.hydrateNestedReferences(wrap);
},
});