claude-plugin-wordpress-manager 2.6.0 → 2.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (49) hide show
  1. package/CHANGELOG.md +61 -0
  2. package/agents/wp-monitoring-agent.md +44 -0
  3. package/agents/wp-site-manager.md +19 -0
  4. package/docs/plans/2026-03-01-tier4-5-implementation.md +1783 -0
  5. package/docs/plans/2026-03-01-tier4-5-observability-automation-design.md +426 -0
  6. package/docs/plans/2026-03-01-wcop-reassessment-v2.6.0.md +403 -0
  7. package/hooks/hooks.json +9 -0
  8. package/package.json +10 -3
  9. package/servers/wp-rest-bridge/build/tools/cwv.d.ts +3 -0
  10. package/servers/wp-rest-bridge/build/tools/cwv.js +196 -0
  11. package/servers/wp-rest-bridge/build/tools/ga4.d.ts +3 -0
  12. package/servers/wp-rest-bridge/build/tools/ga4.js +323 -0
  13. package/servers/wp-rest-bridge/build/tools/index.js +15 -0
  14. package/servers/wp-rest-bridge/build/tools/plausible.d.ts +3 -0
  15. package/servers/wp-rest-bridge/build/tools/plausible.js +207 -0
  16. package/servers/wp-rest-bridge/build/tools/slack.d.ts +3 -0
  17. package/servers/wp-rest-bridge/build/tools/slack.js +129 -0
  18. package/servers/wp-rest-bridge/build/tools/wc-workflows.d.ts +3 -0
  19. package/servers/wp-rest-bridge/build/tools/wc-workflows.js +222 -0
  20. package/servers/wp-rest-bridge/build/wordpress.d.ts +18 -0
  21. package/servers/wp-rest-bridge/build/wordpress.js +139 -0
  22. package/skills/wordpress-router/SKILL.md +1 -1
  23. package/skills/wordpress-router/references/decision-tree.md +8 -2
  24. package/skills/wp-alerting/SKILL.md +142 -0
  25. package/skills/wp-alerting/references/alert-thresholds.md +79 -0
  26. package/skills/wp-alerting/references/escalation-paths.md +92 -0
  27. package/skills/wp-alerting/references/report-scheduling.md +142 -0
  28. package/skills/wp-alerting/references/slack-integration.md +109 -0
  29. package/skills/wp-alerting/scripts/alerting_inspect.mjs +150 -0
  30. package/skills/wp-analytics/SKILL.md +158 -0
  31. package/skills/wp-analytics/references/analytics-dashboards.md +83 -0
  32. package/skills/wp-analytics/references/cwv-monitoring.md +101 -0
  33. package/skills/wp-analytics/references/ga4-integration.md +76 -0
  34. package/skills/wp-analytics/references/plausible-setup.md +92 -0
  35. package/skills/wp-analytics/references/traffic-attribution.md +92 -0
  36. package/skills/wp-analytics/scripts/analytics_inspect.mjs +153 -0
  37. package/skills/wp-content-attribution/SKILL.md +1 -0
  38. package/skills/wp-content-optimization/SKILL.md +1 -0
  39. package/skills/wp-content-workflows/SKILL.md +142 -0
  40. package/skills/wp-content-workflows/references/content-lifecycle-hooks.md +131 -0
  41. package/skills/wp-content-workflows/references/multi-channel-actions.md +151 -0
  42. package/skills/wp-content-workflows/references/schedule-triggers.md +118 -0
  43. package/skills/wp-content-workflows/references/trigger-management.md +159 -0
  44. package/skills/wp-content-workflows/references/wp-action-hooks.md +114 -0
  45. package/skills/wp-content-workflows/scripts/workflow_inspect.mjs +202 -0
  46. package/skills/wp-monitoring/SKILL.md +2 -0
  47. package/skills/wp-search-console/SKILL.md +1 -0
  48. package/skills/wp-social-email/SKILL.md +1 -0
  49. package/skills/wp-webhooks/SKILL.md +1 -0
@@ -0,0 +1,92 @@
1
+ # Traffic Attribution
2
+
3
+ ## UTM Parameter Standards
4
+
5
+ UTM (Urchin Tracking Module) parameters tag URLs to track marketing campaign performance.
6
+
7
+ ### Required Parameters
8
+ | Parameter | Purpose | Example |
9
+ |-----------|---------|---------|
10
+ | `utm_source` | Traffic origin | `google`, `facebook`, `newsletter` |
11
+ | `utm_medium` | Marketing channel | `cpc`, `email`, `social`, `referral` |
12
+ | `utm_campaign` | Campaign name | `spring-sale-2024`, `black-friday` |
13
+
14
+ ### Optional Parameters
15
+ | Parameter | Purpose | Example |
16
+ |-----------|---------|---------|
17
+ | `utm_term` | Paid search keyword | `running+shoes` |
18
+ | `utm_content` | Ad variation / CTA | `cta-button-red`, `hero-banner` |
19
+
20
+ ### URL Format
21
+ ```
22
+ https://example.com/page?utm_source=google&utm_medium=cpc&utm_campaign=spring-sale
23
+ ```
24
+
25
+ ## Source/Medium Mapping
26
+
27
+ ### Standard Mappings in GA4
28
+ | Source/Medium | Description |
29
+ |---------------|-------------|
30
+ | `google / organic` | Google organic search |
31
+ | `google / cpc` | Google Ads paid search |
32
+ | `facebook / social` | Facebook organic posts |
33
+ | `facebook / cpc` | Facebook paid ads |
34
+ | `newsletter / email` | Email marketing campaigns |
35
+ | `(direct) / (none)` | Direct traffic or untagged |
36
+ | `referral / referral` | Incoming links from other sites |
37
+
38
+ ### Plausible Source Mapping
39
+ Plausible uses `visit:source` which maps to the referrer or `utm_source`:
40
+ - Organic search: `Google`, `Bing`, `DuckDuckGo`
41
+ - Social: `Facebook`, `Twitter`, `LinkedIn`
42
+ - UTM-tagged: uses the `utm_source` value directly
43
+
44
+ ## Combining GA4 Traffic with WooCommerce Conversions
45
+
46
+ ### Data Flow
47
+ 1. **GA4** tracks the user journey: source, medium, pages visited, events
48
+ 2. **WooCommerce** records the transaction: products, revenue, order ID
49
+ 3. **Attribution** connects which traffic source led to which purchase
50
+
51
+ ### Attribution Models
52
+ | Model | Logic | Best For |
53
+ |-------|-------|----------|
54
+ | Last click | Credits the last touchpoint before conversion | Simple campaigns |
55
+ | First click | Credits the first touchpoint in the journey | Brand awareness |
56
+ | Linear | Equal credit to all touchpoints | Multi-touch evaluation |
57
+ | Data-driven | ML-based credit distribution (GA4 default) | Complex funnels |
58
+
59
+ ### Implementation Steps
60
+ 1. Ensure GA4 enhanced e-commerce tracking is active (via Site Kit or GTM)
61
+ 2. Map WooCommerce order IDs to GA4 transaction events
62
+ 3. Use `ga4_conversions` tool with `purchase` event to get revenue by source
63
+ 4. Cross-reference with WooCommerce order data for product-level attribution
64
+
65
+ ## Cross-Platform Discrepancy Analysis
66
+
67
+ ### Common Causes of Data Differences
68
+ | Issue | GA4 Impact | Plausible Impact |
69
+ |-------|-----------|-----------------|
70
+ | Ad blockers | Under-reports (blocked) | Under-reports (blocked) |
71
+ | Cookie consent | Under-reports if declined | No impact (cookieless) |
72
+ | Bot traffic | Filtered (mostly) | Filtered |
73
+ | SPA navigation | May miss if not configured | Tracks via History API |
74
+ | Caching | CDN may cache tracking | Same |
75
+ | Sampling | Large datasets sampled | No sampling |
76
+
77
+ ### Reconciliation Steps
78
+ 1. Compare total sessions (GA4) vs visits (Plausible) for the same period
79
+ 2. Calculate the gap percentage: typically 10-30% difference is normal
80
+ 3. Check source-level: organic search should be closest between platforms
81
+ 4. Investigate large discrepancies in specific sources or pages
82
+ 5. Use CWV data as an independent third reference for page-level traffic
83
+
84
+ ## Campaign Tracking Best Practices
85
+
86
+ - **Always tag** paid campaign URLs with UTM parameters
87
+ - **Use consistent naming** conventions (lowercase, hyphens, no spaces)
88
+ - **Document all campaigns** in a shared spreadsheet or naming convention guide
89
+ - **Test tagged URLs** before launching campaigns
90
+ - **Monitor `(not set)`** values in GA4 — indicates untagged traffic
91
+ - **Review referral exclusions** in GA4 to prevent self-referrals
92
+ - **Set up conversion goals** in both GA4 and WooCommerce for accurate ROI
@@ -0,0 +1,153 @@
1
+ /**
2
+ * analytics_inspect.mjs — Detect analytics configuration readiness.
3
+ *
4
+ * Checks WP_SITES_CONFIG for GA4, Plausible, and Google API key credentials.
5
+ * Scans for analytics plugins and tracking code.
6
+ *
7
+ * Usage:
8
+ * node analytics_inspect.mjs [--cwd=/path/to/project]
9
+ *
10
+ * Exit codes:
11
+ * 0 — analytics configuration found
12
+ * 1 — no analytics configuration found
13
+ */
14
+
15
+ import { readFileSync, existsSync, readdirSync } from 'node:fs';
16
+ import { join, resolve } from 'node:path';
17
+ import { argv, stdout, exit } from 'node:process';
18
+
19
+ // ---------------------------------------------------------------------------
20
+ // Helpers
21
+ // ---------------------------------------------------------------------------
22
+
23
+ function readFileSafe(filePath) {
24
+ try { return readFileSync(filePath, 'utf-8'); } catch { return null; }
25
+ }
26
+
27
+ function existsSafe(filePath) {
28
+ try { return existsSync(filePath); } catch { return false; }
29
+ }
30
+
31
+ function globDir(dirPath) {
32
+ try { return readdirSync(dirPath); } catch { return []; }
33
+ }
34
+
35
+ // ---------------------------------------------------------------------------
36
+ // Detectors
37
+ // ---------------------------------------------------------------------------
38
+
39
+ function detectGA4Config() {
40
+ const ga4 = { configured: false, indicators: [] };
41
+ const raw = process.env.WP_SITES_CONFIG;
42
+ if (!raw) return ga4;
43
+
44
+ let sites;
45
+ try { sites = JSON.parse(raw); } catch { return ga4; }
46
+ if (!Array.isArray(sites)) return ga4;
47
+
48
+ for (const site of sites) {
49
+ const label = site.id || site.url || 'unknown';
50
+ if (site.ga4_property_id) {
51
+ ga4.configured = true;
52
+ ga4.indicators.push(`ga4_property_id configured for ${label}`);
53
+ }
54
+ if (site.ga4_service_account_key) {
55
+ ga4.indicators.push(`ga4_service_account_key configured for ${label}`);
56
+ }
57
+ }
58
+ return ga4;
59
+ }
60
+
61
+ function detectPlausibleConfig() {
62
+ const pl = { configured: false, indicators: [] };
63
+ const raw = process.env.WP_SITES_CONFIG;
64
+ if (!raw) return pl;
65
+
66
+ let sites;
67
+ try { sites = JSON.parse(raw); } catch { return pl; }
68
+ if (!Array.isArray(sites)) return pl;
69
+
70
+ for (const site of sites) {
71
+ const label = site.id || site.url || 'unknown';
72
+ if (site.plausible_api_key) {
73
+ pl.configured = true;
74
+ pl.indicators.push(`plausible_api_key configured for ${label}`);
75
+ }
76
+ if (site.plausible_base_url) {
77
+ pl.indicators.push(`plausible_base_url: ${site.plausible_base_url}`);
78
+ }
79
+ }
80
+ return pl;
81
+ }
82
+
83
+ function detectGoogleApiKey() {
84
+ const cwv = { configured: false, indicators: [] };
85
+ const raw = process.env.WP_SITES_CONFIG;
86
+ if (!raw) return cwv;
87
+
88
+ let sites;
89
+ try { sites = JSON.parse(raw); } catch { return cwv; }
90
+ if (!Array.isArray(sites)) return cwv;
91
+
92
+ for (const site of sites) {
93
+ const label = site.id || site.url || 'unknown';
94
+ if (site.google_api_key) {
95
+ cwv.configured = true;
96
+ cwv.indicators.push(`google_api_key configured for ${label}`);
97
+ }
98
+ }
99
+ return cwv;
100
+ }
101
+
102
+ function detectAnalyticsPlugins(cwd) {
103
+ const indicators = [];
104
+ const pluginsDir = join(cwd, 'wp-content', 'plugins');
105
+ const plugins = globDir(pluginsDir);
106
+
107
+ const analyticsPlugins = [
108
+ 'google-analytics-for-wordpress',
109
+ 'google-site-kit',
110
+ 'wp-google-analytics-events',
111
+ 'plausible-analytics',
112
+ 'koko-analytics',
113
+ 'matomo',
114
+ 'independent-analytics',
115
+ ];
116
+
117
+ for (const plugin of analyticsPlugins) {
118
+ if (plugins.includes(plugin)) {
119
+ indicators.push(`plugin: ${plugin}`);
120
+ }
121
+ }
122
+ return { found: indicators.length > 0, indicators };
123
+ }
124
+
125
+ // ---------------------------------------------------------------------------
126
+ // Main
127
+ // ---------------------------------------------------------------------------
128
+
129
+ function main() {
130
+ const cwdArg = argv.find(a => a.startsWith('--cwd='));
131
+ const cwd = cwdArg ? resolve(cwdArg.split('=')[1]) : process.cwd();
132
+
133
+ const ga4 = detectGA4Config();
134
+ const plausible = detectPlausibleConfig();
135
+ const googleApiKey = detectGoogleApiKey();
136
+ const plugins = detectAnalyticsPlugins(cwd);
137
+
138
+ const anyConfigured = ga4.configured || plausible.configured || googleApiKey.configured || plugins.found;
139
+
140
+ const report = {
141
+ analytics_configured: anyConfigured,
142
+ ga4: ga4,
143
+ plausible: plausible,
144
+ google_api_key: googleApiKey,
145
+ analytics_plugins: plugins,
146
+ cwd,
147
+ };
148
+
149
+ stdout.write(JSON.stringify(report, null, 2) + '\n');
150
+ exit(anyConfigured ? 0 : 1);
151
+ }
152
+
153
+ main();
@@ -97,3 +97,4 @@ The script checks WooCommerce presence, analytics plugins, UTM tracking setup, c
97
97
  - `wp-content-repurposing` — transform high-ROI content into multi-channel formats
98
98
  - `wp-search-console` — correlate GSC keyword data with WooCommerce conversions for content-commerce attribution
99
99
  - `wp-content-optimization` — prioritize optimization of high-revenue content using attribution data
100
+ - Per correlazione contenuto→conversione completa, combina `wp-analytics` + `wp-content-attribution`
@@ -170,3 +170,4 @@ Use the **`wp-content-strategist`** agent for content optimization workflows tha
170
170
  - **`wp-content-attribution`** — track content sources and attribute traffic
171
171
  - **`wp-programmatic-seo`** — generate SEO-optimized content at scale
172
172
  - **`wp-social-email`** — distribute optimized content across channels
173
+ - Per prioritizzare ottimizzazione con dati CWV, combina `wp-analytics` + `wp-content-optimization`
@@ -0,0 +1,142 @@
1
+ ---
2
+ name: wp-content-workflows
3
+ description: This skill should be used when the user asks about "workflow automation",
4
+ "triggers", "scheduled tasks", "WP-Cron", "content publishing triggers",
5
+ "hook-based actions", "post status transitions", "automated notifications",
6
+ "workflow triggers", "event-driven actions", "content lifecycle hooks",
7
+ "multi-channel actions", "trigger management", or mentions setting up
8
+ automated workflows that fire on WordPress events or schedules.
9
+ version: 1.0.0
10
+ tags: [workflows, triggers, cron, automation, hooks, scheduling]
11
+ ---
12
+
13
+ # WordPress Content Workflows Skill
14
+
15
+ ## Overview
16
+
17
+ Event-driven workflow automation system for WordPress. Combines WP-Cron scheduling, content lifecycle hooks, and WordPress action/filter hooks to trigger multi-channel actions (Slack, email, webhook). Provides trigger creation, management, testing (dry-run), and audit logging. This skill connects WordPress events to notification and action channels, enabling automated responses to content changes, user actions, and scheduled tasks.
18
+
19
+ ## When to Use
20
+
21
+ - User wants to create automated triggers for WordPress events
22
+ - User needs scheduled tasks (cron-based publishing, periodic reports)
23
+ - User asks about post status transitions (draft to published, trash, etc.)
24
+ - User wants to hook into WordPress actions (user_register, comment_post, etc.)
25
+ - User needs multi-channel action routing (Slack + email + webhook on same event)
26
+ - User asks about trigger management (list, test, enable/disable, delete)
27
+ - User wants to set up WooCommerce order-based workflows
28
+ - User needs to audit or troubleshoot existing workflow triggers
29
+
30
+ ## Decision Tree
31
+
32
+ 1. **What type of trigger?**
33
+ - "cron" / "scheduled" / "periodic" → Schedule-Based Triggers (Procedure 1)
34
+ - "on publish" / "post status" / "content change" → Content Lifecycle Hooks (Procedure 2)
35
+ - "on login" / "user register" / "comment" / "plugin" → WP Action/Filter Hooks (Procedure 3)
36
+ - "notify Slack and email" / "multi-channel" → Multi-Channel Action Configuration (Procedure 4)
37
+ - "list triggers" / "test" / "disable" / "delete" → Trigger Management (Procedure 5)
38
+
39
+ 2. **Run detection first:**
40
+ ```bash
41
+ node skills/wp-content-workflows/scripts/workflow_inspect.mjs [--cwd=/path/to/project]
42
+ ```
43
+ This identifies configured action channels, automation plugins, WP-Cron status, and webhook setup.
44
+
45
+ ## Procedures
46
+
47
+ ### Procedure 1: Schedule-Based Triggers
48
+
49
+ See `references/schedule-triggers.md`
50
+ - Configure WP-Cron intervals (hourly, twicedaily, daily, weekly, custom)
51
+ - Set up scheduled content publishing triggers
52
+ - Create recurring health check and report triggers
53
+ - External cron setup (server cron vs WP-Cron)
54
+ - Test scheduled trigger with `wf_create_trigger` using cron schedule type
55
+
56
+ ### Procedure 2: Content Lifecycle Hooks
57
+
58
+ See `references/content-lifecycle-hooks.md`
59
+ - Hook into post status transitions (draft→published, published→trash)
60
+ - Support custom post types (products, portfolios, events)
61
+ - Monitor taxonomy and term changes
62
+ - Track media upload events
63
+ - Create trigger with `wf_create_trigger` using content lifecycle event type
64
+
65
+ ### Procedure 3: WP Action/Filter Hooks
66
+
67
+ See `references/wp-action-hooks.md`
68
+ - Hook into core WordPress actions (user_register, wp_login, comment_post)
69
+ - WooCommerce hooks (woocommerce_new_order, woocommerce_order_status_changed)
70
+ - Plugin activation/deactivation hooks
71
+ - Filter hooks for content transformation workflows
72
+ - Create trigger with `wf_create_trigger` using action hook event type
73
+
74
+ ### Procedure 4: Multi-Channel Action Configuration
75
+
76
+ See `references/multi-channel-actions.md`
77
+ - Map triggers to one or more action channels (Slack, email, webhook)
78
+ - Configure template variables ({{post_title}}, {{user_name}}, {{order_total}})
79
+ - Channel-specific formatting (Block Kit for Slack, HTML for email, JSON for webhook)
80
+ - Rate limiting per channel to prevent flooding
81
+ - Update trigger actions with `wf_update_trigger`
82
+
83
+ ### Procedure 5: Trigger Management
84
+
85
+ See `references/trigger-management.md`
86
+ - List and filter triggers with `wf_list_triggers`
87
+ - Activate/deactivate triggers without deleting (via `wf_update_trigger`)
88
+ - Test triggers in dry-run mode
89
+ - Review trigger audit log
90
+ - Bulk operations (enable/disable all, export/import)
91
+ - Delete stale triggers with `wf_delete_trigger`
92
+
93
+ ## MCP Tools Reference
94
+
95
+ | Tool | Description |
96
+ |------|-------------|
97
+ | `wf_list_triggers` | List all workflow triggers with optional status/type filters |
98
+ | `wf_create_trigger` | Create a new workflow trigger (cron, lifecycle, action hook) |
99
+ | `wf_update_trigger` | Update trigger config, actions, or status (active/inactive) |
100
+ | `wf_delete_trigger` | Delete a workflow trigger (with safety confirmation) |
101
+
102
+ ## Reference Files
103
+
104
+ | File | Content |
105
+ |------|---------|
106
+ | `references/schedule-triggers.md` | WP-Cron patterns, custom intervals, external cron setup |
107
+ | `references/content-lifecycle-hooks.md` | Post status transitions, CPT support, taxonomy changes, media events |
108
+ | `references/wp-action-hooks.md` | Core WP actions, WooCommerce hooks, plugin hooks, filter hooks |
109
+ | `references/multi-channel-actions.md` | Channel config, template variables, formatting, rate limiting |
110
+ | `references/trigger-management.md` | Listing, activate/deactivate, dry-run testing, audit log, bulk ops |
111
+
112
+ ## Recommended Agent
113
+
114
+ Use the **`wp-site-manager`** for automated workflow orchestration that combines trigger creation, multi-channel action routing, and lifecycle management.
115
+
116
+ ## Related Skills
117
+
118
+ - **`wp-alerting`** — shares Slack and SendGrid channels for notification delivery
119
+ - **`wp-monitoring`** — source of health/performance data that may trigger workflows
120
+ - **`wp-webhooks`** — outbound/inbound webhook infrastructure for webhook action channel
121
+ - **`wp-social-email`** — shares SendGrid and Mailchimp config for email actions
122
+
123
+ ## Cross-references
124
+
125
+ - Workflow triggers pair with `wp-alerting` for severity-based notification routing
126
+ - Scheduled triggers depend on WP-Cron config detectable via `wp-monitoring`
127
+ - Webhook actions use `wp-webhooks` infrastructure for outbound delivery
128
+ - Email actions share SendGrid/Mailchimp config with `wp-social-email`
129
+ - WooCommerce hooks connect to `wp-woocommerce` for order-based workflows
130
+
131
+ ## Troubleshooting
132
+
133
+ | Issue | Cause | Resolution |
134
+ |-------|-------|------------|
135
+ | Cron trigger not firing | DISABLE_WP_CRON is true and no server cron configured | Set up server cron job: `*/5 * * * * wget -qO- https://example.com/wp-cron.php` |
136
+ | Content hook missed | Post updated via direct DB query (bypasses hooks) | Ensure content changes go through `wp_update_post()` or REST API |
137
+ | Slack action fails | slack_webhook_url or slack_bot_token not configured | Add Slack credentials to WP_SITES_CONFIG |
138
+ | Email action 403 | SendGrid API key lacks Mail Send permission | Regenerate key with "Mail Send" access in SendGrid dashboard |
139
+ | Duplicate triggers firing | Multiple hooks registered for same event | Review triggers with `wf_list_triggers` and deduplicate |
140
+ | Trigger test fails | Action channel unreachable or credentials expired | Run `workflow_inspect.mjs` to verify channel configuration |
141
+ | WooCommerce hooks silent | WooCommerce not active or hooks not registered | Verify WooCommerce is active; hooks fire only after `woocommerce_init` |
142
+ | Detection script exit 1 | No workflow config found | Add action channel credentials to WP_SITES_CONFIG and install wp-crontrol |
@@ -0,0 +1,131 @@
1
+ # Content Lifecycle Hooks
2
+
3
+ ## Post Status Transitions
4
+
5
+ WordPress fires `transition_post_status` on every status change:
6
+
7
+ | Transition | From → To | Common Use |
8
+ |------------|-----------|------------|
9
+ | Publish | `draft` → `publish` | Notify team of new content |
10
+ | Schedule | `draft` → `future` | Confirm scheduling |
11
+ | Unpublish | `publish` → `draft` | Alert editors |
12
+ | Trash | `publish` → `trash` | Audit log entry |
13
+ | Restore | `trash` → `draft` | Notify original author |
14
+ | Pending review | `draft` → `pending` | Notify reviewers |
15
+
16
+ ### Hook Signatures
17
+
18
+ ```php
19
+ // Generic transition hook
20
+ add_action('transition_post_status', function ($new, $old, $post) {
21
+ if ($new === 'publish' && $old !== 'publish') {
22
+ // First-time publish — trigger workflow
23
+ }
24
+ }, 10, 3);
25
+
26
+ // Specific transition hooks (preferred for performance)
27
+ add_action('draft_to_publish', function ($post) {
28
+ // Fires only on draft → publish transition
29
+ });
30
+
31
+ add_action('pending_to_publish', function ($post) {
32
+ // Fires on pending → publish (after review approval)
33
+ });
34
+ ```
35
+
36
+ ### Trigger Config Example
37
+
38
+ ```json
39
+ {
40
+ "type": "content_lifecycle",
41
+ "event": "draft_to_publish",
42
+ "post_type": "post",
43
+ "actions": [
44
+ { "channel": "slack", "message": ":newspaper: New post published: *{{post_title}}* by {{post_author}}" }
45
+ ]
46
+ }
47
+ ```
48
+
49
+ ## Custom Post Type Support
50
+
51
+ The same transition hooks work for any registered post type:
52
+
53
+ | Post Type | Slug | Example Trigger |
54
+ |-----------|------|-----------------|
55
+ | WooCommerce Product | `product` | Notify when new product goes live |
56
+ | Portfolio | `portfolio` | Share on social when portfolio item published |
57
+ | Event | `event` | Send reminder email on event publish |
58
+ | Landing Page | `page` | Alert marketing team on page publish |
59
+
60
+ Filter by post type in trigger config:
61
+
62
+ ```json
63
+ {
64
+ "event": "draft_to_publish",
65
+ "post_type": ["post", "product"],
66
+ "condition": "post_type IN (post, product)"
67
+ }
68
+ ```
69
+
70
+ ## Taxonomy and Term Changes
71
+
72
+ | Hook | Fires When | Parameters |
73
+ |------|------------|------------|
74
+ | `set_object_terms` | Terms assigned to a post | `$object_id`, `$terms`, `$tt_ids`, `$taxonomy` |
75
+ | `created_term` | New term created | `$term_id`, `$tt_id`, `$taxonomy` |
76
+ | `edited_term` | Term updated | `$term_id`, `$tt_id`, `$taxonomy` |
77
+ | `delete_term` | Term deleted | `$term_id`, `$tt_id`, `$taxonomy`, `$deleted_term` |
78
+
79
+ Example: notify when a post is tagged with "featured":
80
+
81
+ ```json
82
+ {
83
+ "type": "content_lifecycle",
84
+ "event": "set_object_terms",
85
+ "condition": "taxonomy == 'post_tag' AND terms CONTAINS 'featured'",
86
+ "actions": [
87
+ { "channel": "slack", "message": "Post tagged as featured: {{post_title}}" }
88
+ ]
89
+ }
90
+ ```
91
+
92
+ ## Media Upload Events
93
+
94
+ | Hook | Fires When | Parameters |
95
+ |------|------------|------------|
96
+ | `add_attachment` | New media uploaded | `$attachment_id` |
97
+ | `edit_attachment` | Attachment metadata updated | `$attachment_id` |
98
+ | `delete_attachment` | Media file deleted | `$attachment_id` |
99
+ | `wp_handle_upload` | File upload processed | `$upload` array |
100
+
101
+ Example: log large file uploads:
102
+
103
+ ```json
104
+ {
105
+ "type": "content_lifecycle",
106
+ "event": "add_attachment",
107
+ "condition": "filesize > 5MB",
108
+ "actions": [
109
+ { "channel": "webhook", "url": "{{audit_webhook_url}}", "payload": { "event": "large_upload", "file": "{{filename}}", "size": "{{filesize}}" } }
110
+ ]
111
+ }
112
+ ```
113
+
114
+ ## Example: Notify Slack When Blog Post Published
115
+
116
+ ```json
117
+ {
118
+ "name": "Blog Post Published Notification",
119
+ "type": "content_lifecycle",
120
+ "event": "draft_to_publish",
121
+ "post_type": "post",
122
+ "actions": [
123
+ {
124
+ "channel": "slack",
125
+ "message": ":mega: *New blog post published!*\n*Title:* {{post_title}}\n*Author:* {{post_author}}\n*URL:* {{post_url}}",
126
+ "channel_override": "#content-updates"
127
+ }
128
+ ],
129
+ "status": "active"
130
+ }
131
+ ```
@@ -0,0 +1,151 @@
1
+ # Multi-Channel Action Configuration
2
+
3
+ ## Action Channel Types
4
+
5
+ | Channel | Identifier | Required Config | Tool |
6
+ |---------|-----------|-----------------|------|
7
+ | Slack (Webhook) | `slack` | `slack_webhook_url` in WP_SITES_CONFIG | `slack_send_webhook` |
8
+ | Slack (Bot) | `slack_bot` | `slack_bot_token` + `slack_channel` | `slack_send_message` |
9
+ | Email (SendGrid) | `email` | `sendgrid_api_key` in WP_SITES_CONFIG | `sg_send_email` |
10
+ | Webhook (HTTP) | `webhook` | Target URL in action config | Custom HTTP POST |
11
+ | Mailchimp | `mailchimp` | `mailchimp_api_key` in WP_SITES_CONFIG | Mailchimp API |
12
+
13
+ ## Template Variables
14
+
15
+ Common variables available in all action templates:
16
+
17
+ | Variable | Description | Example Value |
18
+ |----------|-------------|---------------|
19
+ | `{{site_url}}` | WordPress site URL | `https://example.com` |
20
+ | `{{site_name}}` | Site title | `My WordPress Site` |
21
+ | `{{timestamp}}` | Event timestamp (ISO 8601) | `2026-03-01T14:30:00Z` |
22
+ | `{{trigger_name}}` | Name of the firing trigger | `Blog Post Published` |
23
+ | `{{post_title}}` | Post title (content events) | `Hello World` |
24
+ | `{{post_url}}` | Post permalink | `https://example.com/hello-world` |
25
+ | `{{post_author}}` | Post author display name | `John Doe` |
26
+ | `{{post_type}}` | Post type slug | `post` |
27
+ | `{{user_name}}` | User display name | `Jane Smith` |
28
+ | `{{user_email}}` | User email address | `jane@example.com` |
29
+ | `{{order_id}}` | WooCommerce order ID | `1234` |
30
+ | `{{order_total}}` | Order total with currency | `$99.00` |
31
+ | `{{order_status}}` | Current order status | `completed` |
32
+
33
+ ## Channel-Specific Formatting
34
+
35
+ ### Slack (Block Kit)
36
+
37
+ ```json
38
+ {
39
+ "channel": "slack",
40
+ "format": "block_kit",
41
+ "blocks": [
42
+ {
43
+ "type": "header",
44
+ "text": { "type": "plain_text", "text": "{{trigger_name}}", "emoji": true }
45
+ },
46
+ {
47
+ "type": "section",
48
+ "fields": [
49
+ { "type": "mrkdwn", "text": "*Post:*\n{{post_title}}" },
50
+ { "type": "mrkdwn", "text": "*Author:*\n{{post_author}}" }
51
+ ]
52
+ }
53
+ ],
54
+ "fallback_text": "{{trigger_name}}: {{post_title}} by {{post_author}}"
55
+ }
56
+ ```
57
+
58
+ ### Email (HTML)
59
+
60
+ ```json
61
+ {
62
+ "channel": "email",
63
+ "to": "team@example.com",
64
+ "subject": "[{{site_name}}] {{trigger_name}}",
65
+ "format": "html",
66
+ "body": "<h2>{{trigger_name}}</h2><p><strong>{{post_title}}</strong> by {{post_author}}</p><p><a href='{{post_url}}'>View Post</a></p>"
67
+ }
68
+ ```
69
+
70
+ ### Webhook (JSON)
71
+
72
+ ```json
73
+ {
74
+ "channel": "webhook",
75
+ "url": "https://api.example.com/events",
76
+ "method": "POST",
77
+ "headers": { "Content-Type": "application/json", "X-Webhook-Secret": "{{webhook_secret}}" },
78
+ "payload": {
79
+ "event": "{{trigger_name}}",
80
+ "post": { "title": "{{post_title}}", "url": "{{post_url}}", "author": "{{post_author}}" },
81
+ "timestamp": "{{timestamp}}"
82
+ }
83
+ }
84
+ ```
85
+
86
+ ## Rate Limiting Per Channel
87
+
88
+ | Channel | Default Limit | Burst | Cooldown |
89
+ |---------|---------------|-------|----------|
90
+ | Slack (Webhook) | 1 msg/sec | 5 msg burst | 1 second |
91
+ | Slack (Bot) | 1 msg/sec per channel | Tier 2 | Varies |
92
+ | Email (SendGrid) | 100 msg/sec (plan-dependent) | — | None |
93
+ | Webhook | 10 req/sec | 20 burst | 100ms |
94
+
95
+ **Rate limit strategy:**
96
+ - Queue actions when rate exceeded
97
+ - Batch low-priority events into digest messages
98
+ - Critical events bypass rate limits (sent immediately)
99
+ - Log rate limit hits for trigger tuning
100
+
101
+ ## Multi-Channel Action Mapping
102
+
103
+ A single trigger can fire multiple actions across channels:
104
+
105
+ ```json
106
+ {
107
+ "actions": [
108
+ { "channel": "slack", "priority": "high" },
109
+ { "channel": "email", "priority": "high" },
110
+ { "channel": "webhook", "priority": "normal" }
111
+ ]
112
+ }
113
+ ```
114
+
115
+ **Priority levels:**
116
+ - `critical` — all channels fire immediately, bypass rate limits
117
+ - `high` — all channels fire immediately, respect rate limits
118
+ - `normal` — queued, batched if necessary
119
+ - `low` — batched into digest (hourly or daily)
120
+
121
+ ## Example: Critical Order — Slack + Email + Webhook
122
+
123
+ ```json
124
+ {
125
+ "name": "Critical Order Alert",
126
+ "type": "action_hook",
127
+ "event": "woocommerce_payment_complete",
128
+ "condition": "order_total > 500",
129
+ "actions": [
130
+ {
131
+ "channel": "slack",
132
+ "priority": "critical",
133
+ "message": ":moneybag: *High-value order!* #{{order_id}} — {{order_total}}"
134
+ },
135
+ {
136
+ "channel": "email",
137
+ "priority": "critical",
138
+ "to": "sales@example.com",
139
+ "subject": "High-value order #{{order_id}} — {{order_total}}",
140
+ "template": "high_value_order"
141
+ },
142
+ {
143
+ "channel": "webhook",
144
+ "priority": "critical",
145
+ "url": "https://crm.example.com/api/orders",
146
+ "payload": { "order_id": "{{order_id}}", "total": "{{order_total}}", "event": "high_value" }
147
+ }
148
+ ],
149
+ "status": "active"
150
+ }
151
+ ```