סוכנות שיווק / מדריך טכני

אוטומציית דוחות שבועיים ללקוחות סוכנות שיווק עם n8n ו-Claude — מדריך שלב אחר שלב

מדריך מלא לבניית pipeline ב-n8n שמושך מכל לקוח את המספרים מ-GA4, Search Console, Google Ads ו-Meta Ads, מזהה אנומליות, מבקש מ-Claude לכתוב את חלק התובנות בקול של הסוכנות, מרכיב PDF ממותג ושולח אותו ללקוח — white label מלא, כל יום ראשון ב-9:00.

קריאה של 15 דקות
בינוני – מתקדם
n8n + Claude API
עודכן: מאי 2026
מה תבנה
קונפיגורציית לקוח (Airtable)
שליפת GA4 / GSC / Ads (במקביל)
זיהוי אנומליות WoW / YoY
Claude כותב תובנות
PDF ממותג (Puppeteer)
אימייל + Slack handoff ל-AM

1. הבעיה — מס הדיווח של יום ראשון בבוקר

כל סוכנות שיווק שעוברת את ה-12 ריטיינרים נופלת על אותו פולחן יום ראשון: AM פותח 4 טאבים לכל לקוח (GA4, Search Console, Google Ads, Meta Ads), מעתיק מספרים לתבנית Google Slides, כותב 3-5 בולטים של "מה קרה השבוע" מהזיכרון, ושולח לפני בדיקת הצהריים מול הלקוח. כפול 30 לקוחות, וכבר שרפת 25-40 שעות אנליסט על דליבראבל שאף אחד לא משלם עליו תוספת — והתובנות לא עקביות בכלל, כי שלושה אנשים שונים כתבו אותן.

מספרים אמיתיים מסוכנות עם 32 לקוחות

ריטיינרים פעילים 32
ממוצע שעות אנליסט לדוח שבועי 1ש' 10ד'
סך שעות דיווח שבועיות (כל הסוכנות) ~38 שעות
דוחות שנשלחים עד 9:00 ביום שני 41%
אנומליות שצפו פרואקטיבית (לא דרך הלקוח) 28%

הקנס הסמוי גדול מהקנס הגלוי. לקוחות שעוזבים בדרך כלל לא מצטטים "הדוח הגיע באיחור" — הם מצטטים "אף פעם לא הבנתי מה באמת עובד אצלי". דוחות שזורקים גרפים יפים נותנים לבעיות להירקב שבועות. הסוכנויות שמשמרות לקוחות הכי טוב הן אלה שהמייל ביום שני שלהן תמיד אומר ברור: "זה עלה כי, זה נפל כי, וזה מה שאנחנו עושים בעניין".

מה זה "דיווח אוטומטי" כאן

זה לא תבנית של Looker Studio עם הלוגו של הלקוח מוחלף. את זה לרוב הסוכנויות יש כבר, וזה בדיוק הסיבה שהלקוחות אומרים שהדוחות שלהם מרגישים גנריים. אוטומציה אמיתית בנויה משלוש שכבות:

  • שכבת נתונים: workflow יחיד ב-n8n לכל הסוכנות שמושך GA4, GSC, Google Ads, Meta Ads במקביל לכל לקוח כל יום שני ב-6:00.
  • שכבת תובנות: Claude קורא את הדלתות של WoW ו-YoY, מזהה את 3-5 הדברים שבאמת שווה לדבר עליהם, וכותב אותם בקול הבית של הסוכנות — לא בסגנון "מספר ה-sessions ירד ב-12.3% week-over-week" של גוגל.
  • שכבת שילוח: PDF ממותג שמורכב עם הלוגו של הלקוח, טוקני הצבע שלו וחתימת מנהל הלקוח, נשלח במייל ללקוח ומפורסם ב-channel של ה-AM ב-Slack לבדיקה ואז שליחה.
תובנה
השיפור הכי גדול בשימור מגיע מזה שהלקוח רואה שילוח עקבי ביום שני. איחור מתפרש כ"לא רואים שהם בשליטה"; דוח-בזמן-עם-תובנה-אמיתית מתפרש כ"הם בעניינים אצלי". אנחנו רואים את הדפוס הזה שוב ושוב בפרויקטי האוטומציה לסוכנויות שיווק שלנו.

2. ארכיטקטורת המערכת

שמונה רכיבים, כל אחד בר-החלפה. שכבת התזמור היא n8n self-hosted כדי שהסוכנות תהיה בעלת כל קרדנציאל וכל שורה של לוגיקת דיווח — לקוחות שונאים שהדוחות שלהם נעצרים בגלל שספק SaaS צד שלישי הוריד אינטגרציה. Airtable מחזיק את הקונפיג של הלקוח כדי שאמנים בלי גישה לקוד יוכלו לשנות לוגו, רשימת KPI או מייל נמען.

המחסנית

n8n (self-hosted)
תזמור. workflow אב יחיד עובר על כל לקוח פעיל, sub-workflows מטפלים בכל מקור.
Claude API
Sonnet לכתיבת התובנות, Haiku לשורות סיכום קצרות ושורות subject.
GA4 Data API
Sessions, conversions, revenue, channel grouping. Service account לסוכנות, property ID ללקוח.
Search Console API
Clicks, impressions, CTR, מיקום ממוצע. Top movers לפי שאילתה ולפי דף.
Google Ads + Meta Ads
Spend, CPA, ROAS, top campaigns לפי דלתא. OAuth ברמת MCC ב-Google, system user token ב-Meta.
Airtable
קונפיג לקוח: טוקני מותג, בחירת KPI, נמענים, AM אחראי, מתגי דוח.
Puppeteer (PDF)
מרנדר HTML עם הלוגו והטוקנים של הלקוח, מייצא ל-PDF/A. DocRaptor כ-fallback.
SMTP + Slack
Postmark לאימייל טרנזקציוני, Slack incoming webhook לערוץ הבדיקה של ה-AM.

הערכת עלות (30 לקוחות, מחזור שבועי)

Claude Sonnet (30 לקוחות x 4 שבועות x ~3,500 tok in / 900 tok out) ~$48
Claude Haiku (subjects + סיכומים) ~$6
VM (n8n + Chromium ל-Puppeteer על Hetzner CCX23) ~$48
Postmark (1,200 מיילים/חודש) ~$15
Airtable team plan ~$60
סה"כ / חודש (30 לקוחות) ~$177

בעלות אנליסט סוכנותית טיפוסית של ~$65 לשעה, החזרה של אפילו 25 מתוך 38 שעות הדיווח השבועיות שווה ~$1,625 לשבוע, או ~$84,500 בשנה. אותה שכבת תזמור משתלבת בשירותי האוטומציה ה-AI הרחבים שלנו.

1

קונפיגורציית לקוח ב-Airtable

כל לקוח הוא שורה אחת. ה-AM צריך להיות מסוגל להעלות לקוח חדש ב-8-10 דקות בלי שום מעורבות של מהנדס — רק מילוי השורה. ה-schema שטוח בכוונה כדי שיהיה אפשר לערוך ב-grid view; קונפיג מקונן יושב ב-JSON שדות שה-AM כמעט לא נוגע בהם.

Schema של Airtable — טבלת `clients`

Airtable — clients table fieldsSCHEMA
client_id            (autonumber, primary)
client_name          (text)         "Acme Coffee Roasters"
status               (select)       active | paused | offboarded
am_owner             (linked)       -> staff table
ga4_property_id      (text)         "properties/376412899"
gsc_site_url         (text)         "sc-domain:acmecoffee.com"
google_ads_customer  (text)         "123-456-7890"
meta_ad_account_id   (text)         "act_998877665544"
report_kpis          (multi-select) sessions, conversions, revenue,
                                    cpa, roas, organic_clicks, ...
brand_logo           (attachment)   client logo PNG, >= 600px wide
brand_primary_hex    (text)         "#0E5C3F"
brand_secondary_hex  (text)         "#F4B860"
brand_tone           (select)       formal | friendly | technical
recipients           (text)         comma-separated emails
slack_review_channel (text)         "#client-acme-internal"
report_day           (select)       Monday | Tuesday | ... (default Mon)
report_locale        (select)       en-US | en-GB | he-IL | ...

טוען n8n: שליפת לקוחות פעילים

n8n Airtable node — list active clientsJSON
{
  "operation": "list",
  "base":  "{{ $credentials.airtable.baseId }}",
  "table": "clients",
  "filterByFormula":
    "AND({status}='active', {report_day}='{{ $today.weekday }}')",
  "fields": [
    "client_id","client_name","ga4_property_id","gsc_site_url",
    "google_ads_customer","meta_ad_account_id","report_kpis",
    "brand_logo","brand_primary_hex","brand_secondary_hex",
    "brand_tone","recipients","slack_review_channel","report_locale"
  ]
}
שים לב
לא לשים טוקני OAuth ב-Airtable, גם לא מוצפנים. טוקנים יושבים ב-credential vault של n8n ומקושרים לפי client_id. אחרת, AM עם הרשאות עריכה לטבלה יכול בטעות לייצא ב-CSV את כל הקרדנציאלים של Ads של כל הלקוחות בקליק אחד.
2

שליפות API במקביל לכל לקוח

לכל לקוח, יורים את כל ארבעת מקורות הנתונים במקביל — אין תלות ביניהם. השליפה הכוללת צריכה להסתיים בפחות מ-6 שניות גם עם cache קר. אם מקור אחד נופל, נופלים בעדינות: בונים את הדוח מהשאר, ושולחים Slack ל-AM שהמקור השבור צריך reauth.

בקשת GA4 Data API

GA4 — runReport (last 7 days vs prior 7 days)JSON
POST https://analyticsdata.googleapis.com/v1beta/{{ $json.ga4_property_id }}:runReport
Authorization: Bearer {{ $credentials.googleSA.token }}
Content-Type: application/json

{
  "dateRanges": [
    { "startDate": "7daysAgo",  "endDate": "yesterday",
      "name": "current" },
    { "startDate": "14daysAgo", "endDate": "8daysAgo",
      "name": "previous" }
  ],
  "dimensions": [
    { "name": "sessionDefaultChannelGroup" }
  ],
  "metrics": [
    { "name": "sessions" },
    { "name": "totalUsers" },
    { "name": "conversions" },
    { "name": "totalRevenue" },
    { "name": "engagementRate" }
  ],
  "limit": 50
}

Search Console — top movers

GSC — searchAnalytics.queryJSON
POST https://www.googleapis.com/webmasters/v3/sites/{{ encodeURIComponent($json.gsc_site_url) }}/searchAnalytics/query
Authorization: Bearer {{ $credentials.googleSA.token }}

{
  "startDate":   "{{ $json.range.start }}",
  "endDate":     "{{ $json.range.end }}",
  "dimensions":  ["query","page"],
  "rowLimit":    250,
  "dataState":   "final",
  "type":        "web"
}

// Run twice (current 7d + prior 7d), then diff in n8n Function node
// to surface top 10 winning queries and top 10 losing queries by clicks.

Google Ads — דוח קמפיינים

Google Ads — GAQL via RESTJSON
POST https://googleads.googleapis.com/v17/customers/{{ $json.google_ads_customer }}/googleAds:search
Authorization:    Bearer {{ $credentials.googleAds.token }}
developer-token:  {{ $credentials.googleAds.devToken }}
login-customer-id: {{ $credentials.googleAds.mccId }}

{
  "query": "
    SELECT
      campaign.id, campaign.name, campaign.status,
      metrics.cost_micros, metrics.clicks, metrics.impressions,
      metrics.conversions, metrics.conversions_value,
      segments.date
    FROM campaign
    WHERE segments.date DURING LAST_7_DAYS
      AND campaign.status != 'REMOVED'
    ORDER BY metrics.cost_micros DESC
    LIMIT 50
  "
}

דפוס שליפה במקביל ב-n8n

מפעילים Split In Batches על רשימת הלקוחות, ובתוך כל איטרציה ארבעה HTTP nodes במקביל שמתחברים ב-Merge node במצב "wait for all". עוטפים כל קריאה חיצונית ב-Try/Catch sub-workflow כדי ש-401 בודד מ-Meta לא יהרוג את כל הריצה.

תובנה
תמיד למשוך עם dataState: final מ-GSC. ברירת המחדל "all" עוברת backfill למשך 2-3 ימים, וה-WoW דלתות שלך ייראו לא נכונות עד יום שלישי בבוקר כשהלקוח יבדוק שוב. ה-trade-off: הדוח שלך מסתיים שלושה ימים לפני יום שני — וזה בסדר, רק תכבד את התאריך בדוח.
3

זיהוי אנומליות (WoW ו-YoY)

אם תזרוק ל-Claude CSV של 50 שורות גולמי ותשאל "מה מעניין?" — תקבל פסקה שמונה את המובן מאליו. הטריק הוא לעשות את החשבון בקוד קודם, להצמיד severity לכל מטריקה, ולהזין ל-Claude רק את הדלתות המתויגות. זה מוריד עלות טוקנים ומכוון את Claude לדבר על 3-5 הדברים הנכונים בכל פעם.

טבלת ספים (לפי מטריקה)

מטריקה בולט מדאיג קריטי
Sessions WoW ±10% ±20% ±35%
Conversions WoW ±15% ±25% ±40%
Revenue WoW ±15% ±25% ±40%
CPA WoW ±12% ±20% ±35%
ROAS WoW ±10% ±18% ±30%
Organic clicks WoW ±12% ±22% ±35%

מסווג אנומליות (n8n Function node)

n8n Function — classify each metric WoW + YoYJS
const thresholds = {
  sessions:        { notable: 10, concerning: 20, critical: 35 },
  conversions:     { notable: 15, concerning: 25, critical: 40 },
  revenue:         { notable: 15, concerning: 25, critical: 40 },
  cpa:             { notable: 12, concerning: 20, critical: 35 },
  roas:            { notable: 10, concerning: 18, critical: 30 },
  organic_clicks:  { notable: 12, concerning: 22, critical: 35 }
};

function classify(metric, current, previous) {
  if (!previous) return { severity: "new", pct: null };
  const pct = ((current - previous) / previous) * 100;
  const t   = thresholds[metric] ?? { notable: 10, concerning: 20, critical: 35 };
  const a   = Math.abs(pct);
  let sev   = "stable";
  if (a >= t.critical)   sev = "critical";
  else if (a >= t.concerning) sev = "concerning";
  else if (a >= t.notable)    sev = "notable";
  return { severity: sev, pct: Number(pct.toFixed(1)),
           direction: pct >= 0 ? "up" : "down" };
}

const out = $input.all().map(item => {
  const r = item.json;
  return {
    metric: r.metric,
    current: r.current,
    previous_week: r.previous,
    previous_year: r.previous_yoy,
    wow: classify(r.metric, r.current, r.previous),
    yoy: classify(r.metric, r.current, r.previous_yoy)
  };
});

return out;

אחרי הסיווג, מסננים רק את המטריקות המתויגות notable, concerning או critical ושולחים את הרשימה המסוננת ל-Claude. השורות "stable" עדיין מופיעות בטבלת הנתונים בדוח — הן פשוט לא מקבלות זמן מסך בחלק התובנות.

4

Prompt תובנות של Claude

חלק התובנות זה המקום שבו דוח אוטומטי חי או מת. prompt גרוע מייצר משפטים בסגנון "Sessions ירדו ב-12.3% week-over-week" — משפט שהלקוח היה יכול לייצר לבד מהטבלה. prompt טוב גורם ל-Claude לבחור 3-5 דברים שבאמת שווה להגיד עליהם, לנסח כל אחד בקול הסוכנות, ולחלק אותם לניצחונות, חששות וצעדים הבאים.

ה-system prompt

Claude system prompt — weekly insight writerTXT
You are the senior account strategist at {{ agency_name }} writing
the weekly recap section for one client. Your job is to pick the 3-5
things actually worth saying this week and write them in plain language
the client's marketing director can forward to their CEO unedited.

CLIENT CONTEXT:
- Client: {{ client_name }}
- Industry: {{ client_industry }}
- Primary KPI: {{ primary_kpi }}
- Tone: {{ brand_tone }} (formal | friendly | technical)
- Locale: {{ report_locale }}  // respond in this language
- This week's range: {{ range_label }}

INPUT DATA:
- Anomaly-classified metrics (only severity != stable provided)
- Top 10 winning organic queries WoW
- Top 10 losing organic queries WoW
- Top 5 ad campaigns by spend with ROAS deltas
- Notes from the AM (if any) — these take priority over data

OUTPUT — strict JSON, no prose:
{
  "headline": "one sentence the client would forward to their CEO",
  "wins":     ["1-2 sentence bullet", ...],   // 1-3 items
  "concerns": ["1-2 sentence bullet", ...],   // 0-3 items
  "next_steps": ["1-2 sentence bullet", ...], // 1-3 items
  "subject_line": "<= 60 chars, no emoji, no client name"
}

RULES:
- Never just say "sessions decreased by X%". Say WHY it likely happened
  using the supplied query/campaign movers as evidence.
- Never invent a cause not supported by the data or AM notes.
- If a metric is "critical" down, it must appear in concerns.
- If primary KPI is up week-over-week AND year-over-year, lead the
  headline with that.
- Never reference seasonality unless YoY data shows the same pattern.
- Voice: write like a smart human strategist, not a dashboard.

קריאת n8n HTTP Request ל-Claude

n8n HTTP Request — Claude messages callJSON
{
  "method": "POST",
  "url": "https://api.anthropic.com/v1/messages",
  "headers": {
    "x-api-key": "{{ $credentials.anthropic.apiKey }}",
    "anthropic-version": "2023-06-01",
    "content-type": "application/json"
  },
  "body": {
    "model": "claude-sonnet-4-5",
    "max_tokens": 1200,
    "system": "{{ $json.systemPrompt }}",
    "messages": [
      {
        "role": "user",
        "content": "ANOMALIES:n{{ JSON.stringify($json.anomalies) }}nnQUERY MOVERS:n{{ JSON.stringify($json.gscMovers) }}nnCAMPAIGN MOVERS:n{{ JSON.stringify($json.adsMovers) }}nnAM NOTES:n{{ $json.amNotes || 'none' }}"
      }
    ]
  }
}

דוגמת פלט (לקוח ישראלי)

Claude — example output (קולקציית קפה אקמה, שבוע 28 באפריל)JSON
{
  "headline": "השבוע החזק ביותר ברווח אורגני ברבעון, על רקע עליית התנועה לדף יירגצ'ף החדש שתופס גם שאילתות מותג וגם שאילתות לא-מותג.",
  "wins": [
    "ההכנסה האורגנית עלתה ב-28% מול שבוע שעבר ו-41% YoY. הדף החדש (עלה ב-14 באפריל) הוסיף 1,240 קליקים משאילתות כמו 'קפה אתיופי סינגל אוריג'ין' ו'יירגצ'ף מול סידאמו'.",
    "ROAS של קמפיין Search Brand עלה מ-6.1x ל-8.4x אחרי ניקוי שליליות ביום שלישי שעבר — בזבוז על שאילתות 'מכונת קפה' ירד ל-3% מהתקציב."
  ],
  "concerns": [
    "ב-Meta Advantage+ ה-CPA קפץ מ-$18 ל-$27 (+50%). רענון הקריאייטיב שעלה ביום שישי מתעייף מהר — ה-frequency ב-adset המוביל עומד על 4.2."
  ],
  "next_steps": [
    "להחליף את שני הקריאייטיבים עם ה-frequency הגבוה ב-Meta בווריאציות ליום האם, עד יום רביעי.",
    "לבנות לינקים פנימיים מהדפים הקיימים (סידאמו, גואטמלה) לדף יירגצ'ף כדי להגביר את התאוצה ב-SEO."
  ],
  "subject_line": "אקמה - שבועי: שבוע ההכנסה הטוב ברבעון"
}
תובנה
שדה ה-AM notes הוא מנוף האיכות הכי משמעותי בכל המערכת. הערה של שתי שורות בסגנון "הלקוח השיק תמחור חדש ביום רביעי, צפויה ירידה זמנית בהרשמות" מונעת מ-Claude להעלות אזעקת שווא, ונקראת אצל הלקוח כהוכחה שאתה באמת מכיר את העסק שלו. הפוך את כתיבת ההערה לחלק קבוע מסיכום השבוע של ה-AM ביום שישי.
5

הרכבת PDF ממותג

מרנדרים את הדוח כ-HTML עם טוקני המותג של הלקוח, ואז ממירים ל-PDF דרך Puppeteer. הדפוס הזה מאפשר התאמה אישית בלתי מוגבלת לכל לקוח (לוגו, צבעים, פונטים, סדר סקציות) בלי קוד פר-לקוח. תבנית ה-HTML יושבת ב-repo של n8n, הטוקנים מגיעים מהשורה ב-Airtable.

מבנה ה-HTML של הדוח

report-template.html — handlebars stubHTML
<!doctype html>
<html lang="{{ locale }}" dir="{{ direction }}">
<head>
  <meta charset="utf-8">
  <style>
    :root {
      --brand-primary:   {{ brand_primary_hex }};
      --brand-secondary: {{ brand_secondary_hex }};
    }
    body { font-family: Inter, "Heebo", sans-serif; color: #1a1a1a; }
    .cover { background: var(--brand-primary); color: white; padding: 60px; }
    .section h2 { color: var(--brand-primary); border-bottom: 2px solid var(--brand-secondary); }
    .kpi-grid  { display: grid; grid-template-columns: repeat(4, 1fr); gap: 12px; }
    .kpi       { background: #f7f7f7; padding: 18px; border-inline-start: 4px solid var(--brand-primary); }
  </style>
</head>
<body>

  <section class="cover">
    <img src="{{ brand_logo_url }}" height="48">
    <h1>Weekly Performance Report</h1>
    <p>{{ client_name }} — {{ range_label }}</p>
  </section>

  <section class="section">
    <h2>Headline</h2>
    <p class="lead">{{ insight.headline }}</p>
  </section>

  <section class="section">
    <h2>KPIs</h2>
    <div class="kpi-grid">
      {{#each kpis}}
        <div class="kpi">
          <div class="label">{{ label }}</div>
          <div class="value">{{ value }}</div>
          <div class="delta {{ delta_class }}">{{ delta_label }}</div>
        </div>
      {{/each}}
    </div>
  </section>

  <section class="section">
    <h2>Wins</h2>
    <ul>{{#each insight.wins}}<li>{{ this }}</li>{{/each}}</ul>
  </section>

  <section class="section">
    <h2>Concerns</h2>
    <ul>{{#each insight.concerns}}<li>{{ this }}</li>{{/each}}</ul>
  </section>

  <section class="section">
    <h2>Next Steps</h2>
    <ul>{{#each insight.next_steps}}<li>{{ this }}</li>{{/each}}</ul>
  </section>

  <footer>
    Prepared by {{ am_name }} · {{ agency_name }} · {{ today }}
  </footer>
</body>
</html>

רינדור Puppeteer (n8n Code node)

n8n Code node — render HTML to PDFJS
const puppeteer  = require('puppeteer');
const Handlebars = require('handlebars');

const tpl  = Handlebars.compile($input.first().json.templateHtml);
const html = tpl($input.first().json.report);

const browser = await puppeteer.launch({
  args: ['--no-sandbox','--disable-dev-shm-usage']
});
const page    = await browser.newPage();
await page.setContent(html, { waitUntil: 'networkidle0' });

const pdf = await page.pdf({
  format: 'A4',
  printBackground: true,
  margin: { top: '20mm', bottom: '20mm', left: '15mm', right: '15mm' }
});

await browser.close();

return [{
  binary: {
    report_pdf: {
      data: pdf.toString('base64'),
      mimeType: 'application/pdf',
      fileName: `${$json.report.client_slug}-week-${$json.report.iso_week}.pdf`
    }
  }
}];
אבטחה
הרץ את Puppeteer בקונטיינר Docker נפרד בלי גישה לרשת — Chromium הוא משטח תקיפה גדול וכל מה שהוא צריך זה את ה-HTML המקומי. אם פעם URL של לוגו לקוח ייפרץ, ה-renderer לא יוכל לזלוג שום דבר כי אין לו דרך לצאת לאינטרנט הציבורי מתוך הקונטיינר.
6

שילוח + Handoff ל-AM

יש שני מודלים של שילוח. האוטומטי לחלוטין שולח את ה-PDF היישר ללקוח ב-9:00 ביום שני. המפוקח נופל ל-channel של ה-AM ב-Slack ב-7:00 לבדיקה של 60 שניות וקליק "שלח" — הבחירה הנכונה בתקופת ההרצה, כי היא בונה את האמון של ה-AM לפני שאתה נותן לו לוותר על הבקרה.

payload בדיקה ב-Slack

Slack — incoming webhook (Block Kit)JSON
{
  "channel": "{{ $json.client.slack_review_channel }}",
  "blocks": [
    {
      "type": "header",
      "text": { "type": "plain_text",
                "text": ":memo: {{ $json.client.client_name }} — weekly draft ready" }
    },
    {
      "type": "section",
      "text": { "type": "mrkdwn",
                "text": "*Headline:* {{ $json.report.insight.headline }}" }
    },
    {
      "type": "section",
      "fields": [
        { "type": "mrkdwn",
          "text": "*Subject:*n{{ $json.report.insight.subject_line }}" },
        { "type": "mrkdwn",
          "text": "*Recipients:*n{{ $json.client.recipients }}" }
      ]
    },
    {
      "type": "actions",
      "elements": [
        { "type": "button", "text": { "type": "plain_text",
          "text": "Send to client" }, "style": "primary",
          "action_id": "send_report",
          "value": "{{ $json.report.id }}" },
        { "type": "button", "text": { "type": "plain_text",
          "text": "Edit draft" }, "url": "{{ $json.report.editor_url }}" },
        { "type": "button", "text": { "type": "plain_text",
          "text": "Hold" }, "style": "danger",
          "action_id": "hold_report",
          "value": "{{ $json.report.id }}" }
      ]
    }
  ]
}

שליחת אימייל יוצא (Postmark)

Postmark — send-with-attachmentJSON
POST https://api.postmarkapp.com/email
X-Postmark-Server-Token: {{ $credentials.postmark.token }}

{
  "From":      "{{ $json.client.am_name }} <{{ $json.client.am_email }}>",
  "To":        "{{ $json.client.recipients }}",
  "Subject":   "{{ $json.report.insight.subject_line }}",
  "HtmlBody":  "{{ $json.report.email_html }}",
  "TextBody":  "{{ $json.report.email_text }}",
  "MessageStream": "outbound",
  "Attachments": [{
    "Name":        "{{ $json.report.pdf_filename }}",
    "Content":     "{{ $json.report.pdf_base64 }}",
    "ContentType": "application/pdf"
  }],
  "TrackOpens":  true,
  "Tag":         "weekly-report",
  "Metadata": {
    "client_id": "{{ $json.client.client_id }}",
    "iso_week":  "{{ $json.report.iso_week }}"
  }
}

להגדיר את ה-From לכתובת של ה-AM (עם SPF/DKIM תקינים דרך Postmark) זה ההבדל בין "זה נראה כמו אוטומציה שיווקית" ובין "זה נראה כמו מנהל הלקוח שלי". תמיד לשלוח TrackOpens: true ולשמור את אירוע הפתיחה ב-Postgres — שיעור הפתיחה הוא האינדיקטור הכי חזק לכך שהדוח באמת נקרא. אותו דפוס מניע גם את פרויקטי האוטומציה ל-SaaS שלנו, שם זהות שולח אישית מזיזה את שיעור התשובות באופן דרמטי.

9. שכבת white label

מערכת white label אמיתית היא הרבה יותר מהחלפת לוגו. היא שולטת בשלוש שכבות לכל לקוח: זהות חזותית (לוגו, פונטים, טוקני צבע), קול (בורר tone שמכופף את סגנון הכתיבה של Claude), והקרדיטים בתחתית (ה-AM שלך, הדומיין שלך, אפשרות ל-co-branding). כשעושים את זה נכון, הדוח נראה כמו המוצר של הסוכנות אבל מרגיש כמו מסמך פנימי של הלקוח.

טוקני מותג לפי לקוח

טוקן מקור בשימוש ב-
brand_primary_hex Airtable שער, כותרות, פס הדגשה ב-KPI
brand_secondary_hex Airtable קווי מפריד, צבע הדגשה בגרפים
brand_logo Airtable attachment פינה עליונה של עמוד השער
brand_tone Airtable select system prompt של Claude
am_name + am_email טבלת staff תחתית + From של האימייל
report_locale Airtable פורמט מספרים, שמות ימים, מטבע

בקרת קול

השדה brand_tone ב-Airtable מחליף בלוק פסקה אחד בתחתית ה-system prompt של Claude. המימוש הפשוט ביותר עם שלוש פרסטים מכסה 90% מהלקוחות:

  • פורמלי: "כתוב בטון מדוד ומקצועי. משפטים שלמים. בלי קיצורים. הוביל בנתונים, סיים בפרשנות."
  • חברי: "כתוב כמו עמית חכם שמסביר על קפה. קיצורים בסדר. הוביל בלקח האנושי, לא באחוז."
  • טכני: "כתוב למהנדס growth פנימי. מינוח שיווקי מדויק. הראה את החשבון כשרלוונטי. דלג על ה-cheerleading."

דוחות רב-לשוניים

הטוקן report_locale שולט בשלושה דברים: השפה ש-Claude מתבקש להגיב בה ("respond in Hebrew" / "respond in Spanish"), פורמט המספרים (1,234.5 מול 1.234,5), ושמות הימים והחודשים שמרונדרים בשער הדוח. תבנית ה-HTML משתמשת ב-Intl.NumberFormat(locale) ואותה תבנית מטפלת בלקוחות לטיניים ובלקוחות RTL בלי לפצל קוד.

תובנה
תתנגד לדחף להוריד white label עד ברמת הסוכנות. השם שלך תמיד צריך להופיע בפוטר באותיות מיקרוסקופיות — לקוחות זזים, ודוח שיישמר אצלם בתיק עוד שלוש שנים צריך עדיין להוביל בחזרה למי שבנה את הקשר.

10. כשלים נפוצים ופתרונות

שלושה דפוסי כשל מופיעים כמעט בכל הרצה. הם זולים לתכנון ביום הראשון, ויקרים ל-retrofit אחרי שתשעים ימים של דוחות כבר יצאו ללקוחות.

כשל 1: אזעקת שווא בשבוע של השקה ידועה

סימפטום: הלקוח השיק עמוד תמחור חדש ביום רביעי. הרשמות יום שלישי ירדו 38% בדיוק כפי שצפוי. דוח יום שני פותח עם "חשש קריטי: ירידה של 38% בהרשמות", וה-CEO של הלקוח מתקשר לפני הצהריים.

פתרון: שדה ה-AM notes. מוסיפים טבלת client_events ב-Airtable עם תאריך, תווית וכיוון. מוזרק אוטומטית ל-prompt של Claude עם הכלל: "אם נרשם אירוע לקוח בטווח הדוח, השתמש בו כסיבה והורד severity ב-tier אחד."

כשל 2: פג תוקף טוקן ביום שני בבוקר

סימפטום: ה-OAuth של Google Ads פג ביום ראשון בלילה. 12 דוחות יוצאים ב-9:00 ביום שני עם סקציית Ads ריקה כי ה-workflow בלע את ה-401.

פתרון: בדיקת בריאות לקרדנציאלים בשבת בערב — בקשת dummy לכל קרדנציאל OAuth, והודעת Slack לבעלי הסוכנות אם משהו מחזיר 401. מרעננים טוקנים פרואקטיבית ולא ריאקטיבית. חלון השבת משאיר את יום ראשון פנוי ל-reauth ידני.

כשל 3: Claude ממציא סיבה

סימפטום: Sessions שטוחים, אבל Claude כותב "עדכון האלגוריתם האחרון של גוגל כנראה תרם לירידה". לא היה שום עדכון אלגוריתם. ה-AM צריך לחזור על הדוח ולנקות.

פתרון: שני כללים ב-system prompt — "לעולם אל תזכיר עדכון של Google או Meta אלא אם זה מופיע מפורשות בשדה AM-notes" ו"לעולם אל תמציא סיבה שלא נתמכת ב-query/campaign movers בקלט". פעם בחודש, בודקים 5 דוחות אקראיים ומוסיפים ניסוחים אסורים חדשים ככל שתופסים כאלה.

11. תוצאות נמדדות — אחרי 90 יום

מספרים מהרצה אמיתית בסוכנות דיגיטלית עם 32 לקוחות (4 AMs, 2 אסטרטגים בכירים, מיקס ריטיינרים של SEO ופרסום בממוצע של 4,200$/חודש). אין שינוי בהיצע השירות בתקופת הניסוי — השיפור מגיע כולו מהזמן ששוחרר, מהשילוח בזמן ומאיכות התובנות.

שעות דיווח שנחסכו
29 ש' / שבוע
ב-32 ריטיינרים
שילוח בזמן ביום שני
98%
לעומת 41% בקו הבסיס
עליית NPS לקוחות
+19
נמדד אחרי 90 יום
שימור לוגואים
+11pp
12 חודשים נע

המטריקה המעניינת ביותר בתוך הסוכנות היא מה ה-AMs עושים עם 29 השעות שנחסכו: יותר שיחות אסטרטגיה, יותר אופטימיזציות פרואקטיביות בין מחזורי דיווח, ורוחב פס לקחת ריטיינרים חדשים בלי לשכור. שיפור השימור (עלייה של 11 נקודות אחוז בשימור לוגואים על פני 12 חודשים) היה ההשפעה הגדולה ביותר על ההכנסה — והוא נהיה גלוי רק בנקודה של תשעה חודשים.

שיעור פתיחת אימייל על הדוח השבועי התייצב על 71% לרוחב הפורטפוליו. כל לקוח שיורד מתחת ל-50% הוא סימן שהוא התנתק — המערכת מסמנת אוטומטית ומציעה ל-AM לקבוע שיחת בדיקה.

12. לוח זמנים ועלות יישום

מסלול DIY
70 – 110 שעות
  • הקמת n8n self-host + קונטיינר Puppeteer: 6–10 שעות
  • קונפיג לקוחות ב-Airtable + טוען n8n: 4–6 שעות
  • OAuth + שליפות במקביל ל-GA4 + GSC + Ads: 14–20 שעות
  • זיהוי אנומליות + כיוון ספים: 8–12 שעות
  • Prompt תובנות של Claude + פרסטים לטון: 12–18 שעות
  • תבנית HTML + טוקני מותג: 14–20 שעות
  • בדיקה ב-Slack + שילוח Postmark: 6–10 שעות
  • הדרכת AM + run-book + ניטור: 6–10 שעות
עם SEOKRU
פריסה ב-4 שבועות
  • שבוע 1: ביקורת על דיווח קיים, נעילת רשימת KPI, עיצוב תבנית HTML
  • שבוע 2: חיווט GA4/GSC/Ads + ספי אנומליות + schema של Airtable
  • שבוע 3: כיוון prompt תובנות מול 4 שבועות של נתונים היסטוריים
  • שבוע 4: פיילוט על 5 לקוחות, הדרכת AM, ואז עלייה לפורטפוליו מלא
  • כולל: פרסטים לטון, סקירת איכות תובנות חודשית, כיוון prompt שוטף
קבל יישום מותאם ←

שאלות נפוצות

כלי דיווח מהמדף פותרים את בעיית שליפת הנתונים ועוצרים שם. הם נותנים ללקוח דאשבורד עם גרפים. החלק הקשה הוא לא להשיג מספרים — אלא חלק התובנות, הכתיבה בקול ה-AM, השליטה במיתוג לפי לקוח והסימון הפרואקטיבי של אנומליות. גישת n8n + Claude מחזיקה את כל ה-pipeline הזה בידיים שלך, ומאפשרת לשנות prompt אחד כדי לשדרג איכות תובנות לכל הלקוחות בבת אחת. Looker Studio עדיין אופציה טובה כשכבת data מוטמעת, אבל הוא לא מחליף את הדליבראבל שהלקוח באמת קורא ביום שני בבוקר.
מספרים אף פעם לא מגיעים מ-Claude. תבנית ה-PDF מרנדרת את המטריקות ישירות מתשובות ה-API, ו-Claude כותב רק את חלק הנרטיב. ה-prompt גם אוסר על Claude להזכיר אחוז שלא הופיע ברשימת האנומליות שסופקה — אם הוא ינסה, הערך לא יתאים למה שמודפס ב-KPI grid וה-AM יזהה את חוסר ההתאמה מיד. פעם בחודש מריצים ביקורת על 5 דוחות כדי לתפוס drift.
כן. הדפוס זהה: HTTP node אחד לכל מקור, OAuth או system token ב-credential vault של n8n, נורמליזציה ל-shape אחד של metrics_snapshot לפני שמסווג האנומליות רץ. בנינו גרסאות עם TikTok Ads, LinkedIn Ads, Bing Ads, Pinterest, Klaviyo, Shopify ו-HubSpot Marketing באותו workflow. העיקרון: להעביר כל מספר ל-schema מנורמל אחד לפני ש-Claude רואה משהו.
משלים, לא מחליף. רוב הסוכנויות שומרות את הפורטל כמבט תמידי (גרפים חיים, drill-down, ייצוא נתונים) ומשתמשות ב-PDF השבועי כנרטיב המתוקצב. ה-PDF הוא מה שנופל לתיבת הדואר של הלקוח, מועבר ל-CEO ומגיע ל-deck הרבעוני של הדירקטוריון. שני המשטחים שואבים מאותה שכבת data של n8n, אז המספרים תמיד מתואמים.
השורה ב-Airtable נושאת report_day ו-report_locale. ה-workflow האב ב-n8n רץ כל שעה ומעבד רק לקוחות שעברו את 6:00 בבוקר יום שני המקומי שלהם. לקוח אמריקאי מזרחי ולקוח ישראלי שניהם מקבלים דוח של "יום שני בבוקר" — הם פשוט נופלים על שורות שונות בלוח הזמנים.
לא ישירות — זה שובר את אשליית הwhite label. ה-AM הוא העורך. שלב הבדיקה ב-Slack נותן לו חלון של 60-90 דקות לכוונן את הכותרת, להוריד בולט מהחששות, או להחזיק את הדוח לחלוטין. בפועל, אחרי חודש של כיוון, AMs עורכים פחות מ-5% מהטיוטות לפני שליחה.
ה-pipeline מטפל רק בנתוני שיווק מצטברים — שום נתון אישי לא זורם דרך Claude. מספרי אימייל וההכנסה הם אגרגטים, לא רשומות בודדות. ללקוחות באירופה, מריצים את n8n + Postgres על VM בפרנקפורט, משתמשים בנקודת הקצה האירופית של Anthropic עם zero-data-retention מופעל, ומתעדים את זרימת הנתונים בנספח DPA של עמוד אחד. אותה תפיסת ציות מופיעה בשירותי האוטומציה ה-AI שלנו.
8-10 דקות ללקוח, ע"י AM בלי שום עזרה הנדסית. ממלאים את שורת ה-Airtable, גוררים את הלוגו, מדביקים GA4 property ID + GSC site URL + Ads customer ID, בוחרים KPI multi-select וטון. ביום שני הקרוב, הלקוח מקבל דוח מלא. החלק האיטי בדרך כלל הוא ה-OAuth: ה-AM צריך מהלקוח הרשאת view על GA4 ו-GSC, וזה לוקח ללקוח כ-4 דקות אם שולחים לו מדריך צעד-צעד.
כן. ה-multi-select של KPI ב-Airtable שולט אילו סקציות מרונדרות. לקוח של פרסום בלבד מקבל דוח בלי סקציית SEO; ריטיינר SEO בלבד לא מקבל סקציית Ads. גם ה-prompt של Claude מסתגל — אם אין קלט של Ads, הוא לא ימציא תצפית על Ads. לקוחות חד-ערוציים עדיין מקבלים דוח באיכות מלאה עם אותו מבנה תובנה-ראשונה.
שלוש שכבות. ראשית, n8n מנסה שוב עם exponential backoff (3 נסיונות, 30 שניות עד 5 דקות). שנית, אחרי 3 כשלים ה-workflow נופל לתבנית דטרמיניסטית שמדפיסה כותרת בסגנון "סיכום ביצועים עבור {{ client_name }} — {{ range_label }}" ומרנדרת KPIs בלי הערות. שלישית, ה-AM מקבל הודעת Slack שמסמנת דוח מורד, כדי שיוכל לכתוב כותרת ידנית קצרה לפני השליחה. ב-18 חודשים האחרונים אף שילוח לא פוספס לחלוטין.

רוצה שזה ייבנה לדיווח של הסוכנות שלך?

SEOKRU פורסת את המערכת הזו בדיוק ב-4 שבועות. אנחנו עושים ביקורת על הדיווח הקיים שלך, מעצבים את תבנית ה-HTML מול המותג שלך, מחווטים GA4/GSC/Ads/Meta לכל ריטיינר פעיל, מכווננים את ה-prompt של Claude מול 4 שבועות של נתונים היסטוריים שלך ומאמנים את ה-AMs על הזרימה החדשה. אתם שומרים על הבעלות על כל רכיב — workflows, prompts, templates, Airtable, הכל.

דבר עם מהנדס אוטומציה לסוכנות