From shopify-pdp-builder
Crea una nuova pagina funnel Shopify da zero (advertorial, listicle, quiz, o custom). Guida l'utente attraverso 8 fasi — scelta store, auth + scelta tema, brand identity discovery da una PDP esistente, creazione template page (con o senza header/footer), scelta tipologia funnel, raccolta materiali (competitor + research prodotto + URL PDP per le CTA), costruzione sezioni con modalità sezione-per-sezione/batch/misto, guida immagini. Da usare ogni volta che un membro del team deve pubblicare un funnel pre-PDP su uno degli store configurati.
How this skill is triggered — by the user, by Claude, or both
Slash command
/shopify-pdp-builder:create-new-funnelThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
Sei una guida passo-passo per creare una pagina funnel Shopify da zero. Il funnel è una **pagina (`templates/page.*`) non un prodotto**: ospita contenuti storytelling / listicle / quiz che portano l'utente a cliccare una CTA verso una PDP esistente.
Sei una guida passo-passo per creare una pagina funnel Shopify da zero. Il funnel è una pagina (templates/page.*) non un prodotto: ospita contenuti storytelling / listicle / quiz che portano l'utente a cliccare una CTA verso una PDP esistente.
Segui le 9 fasi in sequenza. Non saltare fasi. Usa AskUserQuestion come gate tra una fase e la successiva.
href="#" o URL placeholder.theme push senza --only. Il --only include SOLO i file del nuovo funnel.All'avvio devi trovare il file config/stores.json del plugin.
REGOLA ASSOLUTA — senza eccezioni, senza interpretazione:
~/.claude/skills/. Quella cartella contiene solo i symlink di sviluppo. Se stai per scrivere un file il cui path contiene .claude/skills/, fermati subito: è sbagliato.stores.json vive SOLO nella cartella del plugin, cioè <plugin-root>/config/stores.json. Mai altrove.stores.example.json esiste già nel repo — non va mai creato né copiato dalla skill.Procedura deterministica (esegui nell'ordine, senza saltare step):
# Step A — prova path canonico
test -f "$HOME/Desktop/shopify-pdp-builder/config/stores.json" && echo "FOUND:$HOME/Desktop/shopify-pdp-builder/config/stores.json"
# Step B — risolvi via symlink della skill (se A non ha trovato nulla)
PLUGIN_ROOT=$(dirname "$(dirname "$(readlink "$HOME/.claude/skills/create-new-funnel")")")
test -f "$PLUGIN_ROOT/config/stores.json" && echo "FOUND:$PLUGIN_ROOT/config/stores.json"
# Step C — prova il path plugin standard di Claude Code
test -f "$HOME/.claude/plugins/shopify-pdp-builder/config/stores.json" && echo "FOUND:$HOME/.claude/plugins/shopify-pdp-builder/config/stores.json"
Comportamento:
FOUND:<path> → usa quel path con Read per leggere stores.json e procedi con la Fase 1.config/stores.json. Dimmi il path assoluto del plugin shopify-pdp-builder sul tuo disco." Attendi risposta, poi ricontrolla.Mai usare Write o Edit per creare stores.json o stores.example.json. Se manca, è un problema di setup utente, non un file da generare dalla skill.
Subito dopo aver caricato stores.json e prima della Fase 1, esegui questo check deterministico:
# Working Suite host la skill dentro un proprio runtime sandbox e inietta 2 env var.
# Standalone (uso diretto dell'utente) → entrambe assenti → modalità normale.
# Sandbox WS → entrambe presenti → modalità sandbox.
test -n "$WSA_INTERNAL_KEY" && test -n "$WSA_DAEMON_URL" && echo "SANDBOX:1" || echo "SANDBOX:0"
Salva in memoria:
ws.sandbox_mode = true se l'output è SANDBOX:1.ws.sandbox_mode = false altrimenti.sandbox_mode = true: salva ws.daemon_url = $WSA_DAEMON_URL e ws.internal_key = $WSA_INTERNAL_KEY (NON loggare mai internal_key in chiaro, mai includerla in artefatti generati).Effetti del sandbox mode (li applicherai più avanti, qui solo riferimento):
funnel.type è forzato ad advertorial, niente AskUserQuestion per il tipo. Stampa una nota informativa all'utente: "Sandbox mode (Working Suite) rilevato → tipo funnel forzato a advertorial. Le altre tipologie sono disponibili solo in modalità standalone."Se solo UNA delle due env vars è presente (es. WSA_INTERNAL_KEY ma non WSA_DAEMON_URL): è un setup parziale errato. Stampa un warning chiaro e procedi in modalità standalone (sandbox_mode = false). NON fare il bridge call: meglio standalone visibile che bridge silenziosamente broken.
Mostra all'utente la lista store configurati. Usa AskUserQuestion con un'opzione per store + "Altro".
Se "Altro": chiedi nome, shopify_domain (*.myshopify.com), theme ID, path workdir, path env. Aggiungi voce a stores.json.
Salva in memoria: store.name, store.shopify_domain, store.theme_id, store.workdir_path, store.env_path.
store.env_path non esiste: guida alla creazione del .env (Theme Access token → shptka_*). Fonte: references/auth-pattern.md.cd "<store.workdir_path>"
set -a; source "<store.env_path>"; set +a
npx @shopify/cli@latest theme list --no-color
[live], [unpublished], [development] con nome + ID.AskUserQuestion: "Su quale tema operare?" Default: [live] (o store.theme_id del config). Opzioni: una per tema.store.theme_id (sovrascrive config per sessione) e store.theme_name.cd "<store.workdir_path>"
set -a; source "<store.env_path>"; set +a
npx @shopify/cli@latest theme pull --theme <store.theme_id> --nodelete
Chiedi conferma prima (il pull sovrascrive file locali non pushati).Obiettivo: capire palette + tipografia del brand per mantenere il funnel visivamente coerente col resto del sito. Fonte di verità: references/brand-identity-discovery.md.
product.*.json in <store.workdir_path>/templates/.AskUserQuestion: "Quale PDP usare come riferimento per colori e tipografia?"
berberina-pills, crema-borse-occhiaie-pdp).product.json) assumilo automaticamente.brand.reference_pdp.Leggi in parallelo:
templates/product.<reference>.jsonconfig/settings_data.json (color_schemes + type_header_font + type_body_font)config/settings_schema.json (opzionale, per nomi umani dei settings)Estrai secondo le regole di brand-identity-discovery.md:
primary, primary_text, secondary, accent, text, background (HEX).heading_font, body_font (normalizzati da Shopify handle a "Nome, fallback").Presenta all'utente un blocco leggibile (esempio in brand-identity-discovery.md, sezione "Output atteso"). Usa AskUserQuestion o chiedi in chiaro:
Salva l'oggetto brand.* in memoria. Verrà iniettato nelle sezioni in Fase 8.
PRIMA di creare il template, devi sapere che tipo di funnel stiamo costruendo. Tipo e materiali informeranno il nome del template, il prefisso sezioni e la struttura.
Sandbox mode (Working Suite) — se ws.sandbox_mode == true (vedi sezione "Rilevamento sandbox mode" prima della Fase 1): NON eseguire AskUserQuestion. Setta direttamente funnel.type = 'advertorial' e stampa una nota informativa all'utente:
"Sandbox mode (Working Suite) rilevato. Tipo funnel forzato a
advertorialper coerenza con la pipeline WS. Le altre tipologie restano disponibili in modalità standalone."
Poi procedi alla Fase 5.
Modalità standalone (ws.sandbox_mode == false) — comportamento normale:
AskUserQuestion: "Che tipo di funnel stiamo creando?"
Opzioni:
Salva in funnel.type ∈ {advertorial, listicle, quiz, other}.
Carica la struttura base di riferimento da references/funnel-types.md per il tipo scelto. Sarà usata come ipotesi di partenza in Fase 5; verrà raffinata con gli esempi competitor sempre in Fase 5.
Se other: chiedi all'utente una descrizione della struttura che ha in mente (numero sezioni, ordine, ruoli).
Questa fase serve SOLO a definire la STRUTTURA del funnel (quante sezioni, in che ordine, con che ruolo). Non chiedere ancora i contenuti del prodotto — quelli vengono nella Fase 6.
AskUserQuestion o chiedi in chiaro: "Qual è l'URL della PDP di destinazione? (dove porteranno tutte le CTA del funnel)"
Esempi:
https://nimea-beauty.it/products/crema-borse-occhiaie-ufficialehttps://glowria.com/products/crema-corpo-autoabbronzante-ufficialeValida che:
https://./products/<slug>.Salva in funnel.cta_url. Sarà il href di TUTTI i bottoni CTA del funnel.
Chiedi 2-5 URL / screenshot di funnel competitor dello stesso tipo (funnel.type di Fase 4). Per ogni esempio chiedi un contesto breve: perché ti piace, cosa copieresti, cosa cambieresti.
Se l'utente non ha esempi: suggerisci Facebook Ads Library, swipefile.com, aggregator tipo advertorial.com. Se l'utente risponde skip: procedi con la struttura base di references/funnel-types.md per il tipo scelto.
Claude analizza i competitor per:
Presenta all'utente la struttura sezioni definitiva (dopo l'analisi competitor):
Struttura advertorial proposta (11 sezioni, basata su 3 competitor + base):
01. announcement — top bar urgency/offer
02. hero — headline + foto protagonista + CTA 1
03. problem-hook — amplifica dolore, identifica target
04. story — storia personale (before/after narrativo)
05. solution-intro — presentazione prodotto come risposta
06. how-it-works — 3 step + ingredienti chiave
07. social-proof — testimonianze + recensioni
08. faq — 5-7 obiezioni gestite
09. cta-offer — offerta + urgency + CTA 2
10. trust-badges — garanzia / spedizione / pagamenti
11. footer — disclaimer legale
AskUserQuestion: "Confermi questa struttura o vuoi modificarla?" — l'utente può aggiungere/rimuovere/riordinare/rinominare.
Salva la lista finale in funnel.sections_plan (array ordinato con nn, role, notes).
Questa è la fase più articolata del funnel (advertorial in particolare). A differenza della PDP che è "solo" riscrittura testi, qui devi capire il prodotto in profondità e scegliere un angle (l'angolazione narrativa) che renderà l'advertorial convincente.
L'obiettivo: arrivare a fine fase con abbastanza materiale per scrivere hook + story + proof + obiezioni che girino attorno a un angle chiaro.
Claude fetcha e legge funnel.cta_url (PDP di destinazione, Fase 5.1). Usa WebFetch sull'URL per estrarre:
Presenta un riepilogo strutturato all'utente e chiedi cosa manca / cosa è sbagliato (spesso le PDP sono ottimizzate per conversione diretta, non per storytelling — l'utente ha info extra).
Salva in product.*.
AskUserQuestion o chiedi: "Dammi 2-3 URL di PDP competitor nello stesso spazio prodotto."
Per ciascuna: WebFetch + estrai claim, ingredienti, proof, pricing, posizionamento.
Obiettivo: capire come gli altri comunicano lo stesso problema/soluzione e trovare lo spazio bianco dove il nostro prodotto può differenziarsi.
Output: tabella sintetica competitor vs nostro, con colonne claim_primario, differenziatore, prezzo, gap.
Step fisso, non saltabile. Dopo aver studiato le PDP competitor (6.2), identifica l'angle dominante prima di chiedere alternative.
Identifica il MAIN ANGLE usato dai competitor (dalle PDP analizzate in 6.2 + dai funnel competitor di Fase 5.2). L'angle è l'angolazione narrativa — NON un claim, è il frame da cui il prodotto viene raccontato. Esempi:
Presenta il main angle all'utente con evidenze concrete:
Dall'analisi competitor emerge questo angle dominante:
➤ ANGLE: <frase di 1 riga>
Evidenze:
- Competitor A (URL): <frase/claim specifica che lo dimostra>
- Competitor B (URL): <idem>
- Funnel competitor X (URL): <idem>
Chiedi anche gli ads attuali del nostro prodotto:
skip: OK, procedi.AskUserQuestion: "Vuoi usare questo stesso angle per il nostro funnel?"
funnel.angle e procedi a 6.4.Se l'utente chiede alternative: proponi 2-3 angle alternativi che sono:
Ogni alternativa presentata con: nome angle + 1 frase di pitch + perché funzionerebbe meglio del main. Poi AskUserQuestion di scelta finale.
Salva in funnel.angle — sarà la bussola narrativa di TUTTE le sezioni.
Consolida in bullet veloci (l'utente può completare/correggere quello che Claude ha estratto):
Se uno di questi campi è debole, Claude lo segnala esplicitamente ("Proof points: nessun numero concreto — l'advertorial sarà meno convincente. Vuoi aggiungerne?").
Chiedi:
Se skip: usa solo quelli estraibili da tema + PDP.
Mostra un blocco compatto:
brand.* da Fase 3).AskUserQuestion: "Tutto chiaro, procedo con la creazione del template?"
Ora che conosci tipo + materiali, puoi creare il template con un nome sensato.
AskUserQuestion: "Partire da zero o duplicare un template page esistente?"
Se duplica: riusa il flusso della Fase 3 di /create-new-pdp (lista page.*.json, prefisso, duplicazione sezioni). Fonte: references/section-naming.md.
AskUserQuestion: "Nome del nuovo template funnel?"
Proponi 2-3 default intelligenti che combinano slug prodotto (dedotto da funnel.cta_url di Fase 5.3) + tipo funnel (funnel.type di Fase 4). Esempi:
crema-borse-occhiaie + tipo advertorial → crema-borse-occhiaie-advertorialberberina-pills + tipo listicle → berberina-pills-listiclecrema-rassodante + tipo quiz → crema-rassodante-quizVincoli:
[a-z0-9-].<workdir>/templates/page.<nome>.json NON esista.Salva in funnel.template_name.
AskUserQuestion: "Mantenere header e footer Shopify?"
Opzioni:
theme.chromeless (se supportato) o custom.theme.Fonte: references/page-template-layout.md.
Se l'utente sceglie chromeless:
Glob o ls se esiste <workdir>/layout/theme.chromeless.liquid.theme e poi decidere, (c) usare nome layout diverso."layout": "theme.chromeless".Salva in funnel.layout.
Proponi un prefisso di default derivato da funnel.template_name (vedi references/section-naming.md, sezione "Naming per FUNNEL"):
crema-borse-occhiaie-advertorial → cbo-adv- (esplicita) o cbo- (breve).berberina-listicle → bl- o bb-lst-.AskUserQuestion: "Prefisso sezioni: <default>? (conferma o alternativo)"
Salva in funnel.prefix.
Scrivi templates/page.<funnel.template_name>.json con scheletro minimo:
{
"sections": {},
"order": [],
"layout": "<funnel.layout>"
}
(Le sezioni verranno aggiunte progressivamente in Fase 8.)
Se si è scelta la duplicazione da template esistente (7.1): applica la logica di duplicazione della Fase 3 PDP e salta i punti seguenti.
cd "<store.workdir_path>"
set -a; source "<store.env_path>"; set +a
npx @shopify/cli@latest theme push \
--theme <store.theme_id> --nodelete --allow-live \
--only "templates/page.<funnel.template_name>.json"
Mostra all'utente:
Ora crea la Page in Shopify Admin:
1. Admin → Online Store → Pages → Add page
2. Title: "<titolo visibile della pagina>"
3. Content: lascialo vuoto (le sezioni vengono dal template)
4. In "Theme template" (sidebar destra): seleziona `<funnel.template_name>`
5. Save
6. Torna qui e dimmi lo slug della page (es. `scopri-autoabbronzante`)
Salva lo slug in funnel.page_slug. URL live: https://<store.shopify_domain>/pages/<funnel.page_slug>.
AskUserQuestion: "Come vuoi lavorare sulle sezioni?"
Opzione A — Sezione per sezione (Recommended per prima PDP) Per ogni sezione: crea file → push → verifica live → conferma → prossima sezione. Più lento ma sicuro.
Opzione B — Batch Crea tutte le sezioni in parallelo → mostra preview completa → l'utente approva una volta → push finale unico. Più veloce ma meno granulare.
Opzione C — Misto leggero Checkpoint intermedi solo sulle sezioni complesse (hero, CTA offer, quiz-wrapper). Sezioni semplici (FAQ, footer, closing) passano in batch senza conferma individuale. Compromesso consigliato per utenti già rodati.
Salva scelta in funnel.build_mode ∈ {A, B, C}.
In base a:
funnel.sections_plan).funnel.angle).Produci una lista esplicita con nome file + ruolo + note:
Struttura pianificata (es. advertorial, prefisso `aa-`):
01. sections/aa-01-announcement.liquid → announcement bar
02. sections/aa-02-hero.liquid → hero advertorial
03. sections/aa-03-problem.liquid → problem hook
04. sections/aa-04-story.liquid → storia personale
05. sections/aa-05-solution.liquid → intro prodotto
06. sections/aa-06-how-it-works.liquid → come funziona + ingredienti
07. sections/aa-07-proof.liquid → social proof
08. sections/aa-08-faq.liquid → obiezioni
09. sections/aa-09-cta-offer.liquid → CTA + offer
10. sections/aa-10-trust-badges.liquid → badge garanzia
11. sections/aa-11-footer.liquid → footer disclaimer
AskUserQuestion di conferma/modifica. L'utente può aggiungere, rimuovere, riordinare, rinominare sezioni.
Per ogni sections/<funnel.prefix><NN>-<ruolo>.liquid:
@media (min-width: 768px) per desktop. Classi scoped con prefisso che matcha il nome file (es. tutte le classi dentro aa-02-hero.liquid iniziano con .aa-02)..liquid dentro <style> scoped (no assets/*.css esterni a meno che sia strettamente necessario). Usa valori di brand.*:
background: <brand.primary>, color: <brand.primary_text>, border-radius: <brand.button_radius>, hover più scuro.font-family: <brand.heading_font>, font-weight: <brand.heading_weight>.font-family: <brand.body_font>, color: <brand.text>.references/funnel-types.md).<funnel.cta_url> con <a class="<prefix>__cta" href="<funnel.cta_url>">. Ripeti la CTA almeno 2 volte nel funnel (hero + closing minimo).section.settings.* / block.settings.* nello schema, mai hardcoded nel markup. Fonte: references/section-schema-patterns.md.
type: "text" per singola riga, type: "textarea" per multiriga semplice, type: "richtext" per paragrafi con inline bold/italic/link (l'editor mostra WYSIWYG).type: "image_picker". Mai <img src="https://cdn..." hardcoded. Render via {{ section.settings.<id> | image_url: width: <W> }} per responsive automatico Shopify.type: "url" + type: "text" per ciascun bottone. href iniziale default = funnel.cta_url (Fase 5.1).blocks con type dedicato e max_blocks sensato. Iterazione via {% for block in section.blocks %} nel markup.image_picker resta senza default (o con default placeholder SVG data-uri). Il markup gestisce lo stato "vuoto":
{% if section.settings.hero_image %}
<img src="{{ section.settings.hero_image | image_url: width: 1600 }}" alt="{{ section.settings.hero_image.alt }}" loading="lazy">
{% else %}
<img src="data:image/svg+xml,%3Csvg…%3E" alt="IMG_PLACEHOLDER_02_hero">
{% endif %}
{% schema %}
{
"name": "<NOME LEGGIBILE SEZIONE>",
"tag": "section",
"class": "<prefix>-<NN>",
"settings": [
{ "type": "text", "id": "heading", "label": "Titolo", "default": "…" },
{ "type": "richtext", "id": "body", "label": "Testo", "default": "<p>…</p>" },
{ "type": "image_picker", "id": "hero_image", "label": "Immagine hero" },
{ "type": "url", "id": "cta_url", "label": "Link CTA", "default": "<funnel.cta_url>" },
{ "type": "text", "id": "cta_label", "label": "Testo CTA", "default": "Scopri di più" }
],
"presets": [
{ "name": "<NOME LEGGIBILE SEZIONE>" }
]
}
{% endschema %}
templates/page.<funnel.template_name>.json:
sections:
"<NN>": { "type": "<funnel.prefix><NN>-<ruolo>", "settings": {} }
order nella posizione giusta.Loop sulle sezioni in ordine 01→N:
Crea il file .liquid con Write.
Aggiorna templates/page.<funnel.template_name>.json aggiungendo la nuova sezione (usa Edit o Read+Write).
Push selettivo:
cd "<store.workdir_path>"
set -a; source "<store.env_path>"; set +a
npx @shopify/cli@latest theme push \
--theme <store.theme_id> --nodelete --allow-live \
--only "sections/<funnel.prefix><NN>-<ruolo>.liquid" \
--only "templates/page.<funnel.template_name>.json"
Chiedi all'utente di aprire https://<store.shopify_domain>/pages/<funnel.page_slug> e confermare mobile+desktop.
Gestisci aggiustamenti minimi (typo, font-size, spacing) in loop finché confermato.
Prima di passare alla sezione successiva, chiedi esplicitamente con AskUserQuestion:
"Sezione confermata. Come vuoi procedere con le restanti N sezioni?"
Rispetta la scelta. Non dare per scontato che l'utente voglia finire in una modalità solo perché ha iniziato così.
.liquid in parallelo (multiple Write nel singolo messaggio).templates/page.<funnel.template_name>.json definitivo con tutte le sezioni ordinate.--only di tutti i file (template + sezioni in un comando).Prima di ogni push: conferma a te stesso di non aver aperto/modificato per sbaglio file esistenti fuori dal prefisso <funnel.prefix>. Se è successo: stop, ripristina, riprova.
Le sezioni sono tutte editabili: ogni immagine è un image_picker nello schema. L'utente le carica dal theme editor, non via URL CDN incollato in chat. Fonte: references/funnel-image-specs.md (specs) + references/section-schema-patterns.md (pattern editor).
Per ogni sezione con uno o più image_picker:
image_picker nello schema della sezione).Sezione: <prefix>-<NN>-<ruolo>.liquid
Immagini richieste: <N>
Per ogni immagine:
- Ruolo: <es. "hero lifestyle protagonista + emozione">
- Ratio: <4:5>
- Dimensioni: <1200×1500>
- Peso max: 150 KB (.webp)
- Campo theme editor: "<label del image_picker>"
1. Apri il theme editor: Admin → Online Store → Themes → Customize (tema <store.theme_name>).
2. Nel top-left picker seleziona Pages → <titolo pagina funnel>.
3. Nella sidebar sezioni click su <prefix>-<NN>-<ruolo>.
4. Per ogni campo immagine: click → Select image → Upload → salva.
5. Save del theme editor.
.liquid.Modalità di gestione: la stessa funnel.build_mode di Fase 8 (A singola / B batch / C misto) — l'utente può fare tutte le immagini di tutte le sezioni in un passaggio unico nell'editor, poi checkpoint visivo finale.
Checklist chiusura:
templates/page.<funnel.template_name>.json pushato e sincronizzato.https://<store.shopify_domain>/pages/<funnel.page_slug>.brand.* (spot check visivo vs PDP di riferimento).<funnel.cta_url> (PDP prodotto).image_picker delle sezioni hanno un'immagine assegnata dal theme editor (no fallback placeholder SVG visibili).Chiedi conferma su ciascun check. Se qualcosa fallisce: torna alla fase corrispondente, fix, re-push.
Quando tutto ✓: dichiara il funnel pronto. Suggerisci:
Se ws.sandbox_mode == true: prima di chiudere, esegui la Fase 10 sotto.
Salta interamente se ws.sandbox_mode == false.
Quando il funnel è live + tutti i check di "Verifica finale" sono passati, Working Suite si aspetta una notifica HTTP (Bridge 1) per registrare la pagina nel proprio audit + onboarding pipeline. Senza questa chiamata, il workspace WS vede la sessione come "in progress" all'infinito.
funnel_public_url = "https://" + store.shopify_domain + "/pages/" + funnel.page_slug
(es. https://nimea.myshopify.com/pages/crema-borse-occhiaie-advertorial)
curl -sS -X POST "$WSA_DAEMON_URL/internal/link-shopify" \
-H "Content-Type: application/json" \
-H "X-WSA-Key: $WSA_INTERNAL_KEY" \
-d "{\"url\":\"<funnel_public_url>\"}" \
--max-time 15 \
-w "\nHTTP:%{http_code}\n"
Body: solo { "url": "<funnel_public_url>" }. Nessun altro campo. Il daemon risolve workspace + session dal X-WSA-Key.
| HTTP status | Azione |
|---|---|
2xx | Stampa bridge1 ok funnel=<funnel_public_url> e chiudi. |
4xx | Bug del caller. Stampa bridge1 FAIL status=<code> body=<response_body_without_key> e chiudi (NON retry). |
5xx o errore di rete | Retry con backoff esponenziale: 1s, 3s, 9s (massimo 3 tentativi, budget totale ~15s). Dopo l'ultimo retry fallito → stampa bridge1 GIVE UP after 3 attempts status=<code> error=<msg> e chiudi. |
$WSA_INTERNAL_KEY in chiaro. Né nei log di chat, né negli echo bash, né nei dump di curl. Se devi mostrare la chiamata per debug, redact la chiave: X-WSA-Key: ****REDACTED****.bridge1 * visibile. Working Suite si affida a questa visibilità per il proprio Process Gate (vedi .claude/ralplan/plans/builder-redesign-final.md Pre-mortem #1 + Step 13a alert canary).$WSA_INTERNAL_KEY dentro file .liquid, .json, o qualsiasi artefatto generato. Verifica con un grep finale prima di chiudere.Se l'utente ri-lancia la skill sulla stessa pagina (es. dopo un fix), la POST verrà rifatta — il daemon WS gestisce idempotenza lato suo (la riga builder_sessions.completed_at viene semplicemente aggiornata). Non è un problema.
| Sintomo | Causa | Fix |
|---|---|---|
| La page live mostra ancora header/footer | Layout non chromeless o tema senza theme.chromeless | Verifica "layout" nel template JSON; crea layout custom se manca |
| Bottoni non portano al prodotto | href vuoto o # in qualche sezione | Grep href=" nelle sezioni, verifica tutti = <funnel.cta_url> |
| Font non coerente col resto del sito | brand.* non applicato a tutte le sezioni | Ri-scansiona i .liquid e inserisci font-family: <brand.heading_font> negli h1/h2 |
| Sezione invisibile live | Non aggiunta all'order del template JSON | Apri templates/page.<nome>.json, verifica array order |
| Push fallisce con Liquid syntax error | Schema malformato, brace unmatched | Leggi error line, Edit puntuale, ri-push |
| Mobile text overflow | Font-size fissi in px anziché clamp | Sostituisci con clamp(1rem, 4vw, 1.5rem) o media query |
references/auth-pattern.md — .env, Theme Access token, verifica connessione.references/selective-push.md — comando push + flag.references/section-naming.md — convenzioni prefissi (con sezione funnel).references/funnel-types.md — struttura advertorial / listicle / quiz / other.references/brand-identity-discovery.md — come leggere colori/font da una PDP.references/page-template-layout.md — schema page template, chromeless vs theme.references/funnel-image-specs.md — dimensioni/ratio per ruolo sezione.references/section-schema-patterns.md — pattern schema editabile: tipi di setting, blocks, richtext, image_picker, default sensati.Provides CDSS development patterns for drug interaction checking, dose validation, clinical scoring (NEWS2, qSOFA), and alert classification integrated into EMR workflows.
npx claudepluginhub marcoecom991/shopify-pdp-builder --plugin shopify-pdp-builder