{
  "id": "h2yMJwW58C1twKNv",
  "meta": {
    "templateCredsSetupCompleted": true
  },
  "name": "Daily WooCommerce Sales Snapshot \u2192 Slack",
  "tags": [],
  "nodes": [
    {
      "id": "76bb2c69-3f36-4bb3-bea1-b259c6995488",
      "name": "Daily Schedule",
      "type": "n8n-nodes-base.scheduleTrigger",
      "position": [
        32,
        352
      ],
      "parameters": {
        "rule": {
          "interval": [
            {
              "triggerAtHour": 9
            }
          ]
        }
      },
      "typeVersion": 1.2
    },
    {
      "id": "d97ab0ad-59bd-40c7-9c00-ad4cd7d90cab",
      "name": "Fetch WooCommerce Orders",
      "type": "n8n-nodes-base.wooCommerce",
      "position": [
        368,
        224
      ],
      "parameters": {
        "options": {},
        "resource": "order",
        "operation": "getAll",
        "returnAll": true
      },
      "credentials": {
        "wooCommerceApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 1
    },
    {
      "id": "6f674f94-af6f-44b5-88b1-cd7a86716cf0",
      "name": "Filter Paid Orders",
      "type": "n8n-nodes-base.filter",
      "position": [
        544,
        224
      ],
      "parameters": {
        "options": {},
        "conditions": {
          "options": {
            "version": 1,
            "leftValue": "",
            "caseSensitive": true,
            "typeValidation": "strict"
          },
          "combinator": "or",
          "conditions": [
            {
              "id": "87e8c91d-6544-4b2e-b9ea-3838805e5444",
              "operator": {
                "type": "string",
                "operation": "equals"
              },
              "leftValue": "={{ $json.status }}",
              "rightValue": "processing"
            },
            {
              "id": "b3d4838c-b0da-4ce1-b75c-2855a0760268",
              "operator": {
                "name": "filter.operator.equals",
                "type": "string",
                "operation": "equals"
              },
              "leftValue": "={{ $json.status }}",
              "rightValue": "completed"
            }
          ]
        }
      },
      "typeVersion": 2
    },
    {
      "id": "3cdf966f-4f5e-42e9-a2b5-c57bbbcedb8c",
      "name": "Last 24h Orders",
      "type": "n8n-nodes-base.code",
      "position": [
        720,
        224
      ],
      "parameters": {
        "jsCode": "// Filter orders from last 24 hours\nconst cutoff = new Date(Date.now() - 24 * 60 * 60 * 1000);\n\nreturn items.filter(i => new Date(i.json.date_created) >= cutoff);"
      },
      "typeVersion": 2
    },
    {
      "id": "f4274439-a7f5-4301-b61f-cc46cbad7cfa",
      "name": "Calculate Revenue + AOV",
      "type": "n8n-nodes-base.code",
      "position": [
        1056,
        368
      ],
      "parameters": {
        "jsCode": "let revenue = 0;\nlet count = items.length;\nlet currency = null;\n\nfor (const i of items) {\n  revenue += parseFloat(i.json.total || 0);\n  if (!currency) currency = i.json.currency;\n}\n\nconst aov = count > 0 ? revenue / count : 0;\n\nreturn [{ json: { totalRevenue: revenue.toFixed(2), orderCount: count, aov: aov.toFixed(2), currency } }];"
      },
      "typeVersion": 2
    },
    {
      "id": "a7f0c8e1-380a-4bf2-9e02-a1e5d4ceec9e",
      "name": "Calculate Top Products",
      "type": "n8n-nodes-base.code",
      "position": [
        1056,
        80
      ],
      "parameters": {
        "jsCode": "const productMap = {};\n\nfor (const item of items) {\n  for (const line of item.json.line_items || []) {\n    productMap[line.name] = (productMap[line.name] || 0) + line.quantity;\n  }\n}\n\nconst topProducts = Object.entries(productMap)\n  .sort((a,b) => b[1] - a[1])\n  .slice(0,5);\n\nreturn [{ json: { topProducts } }];"
      },
      "typeVersion": 2
    },
    {
      "id": "daf871ef-d441-4de3-971a-1a111c8092ca",
      "name": "Merge Metrics",
      "type": "n8n-nodes-base.merge",
      "position": [
        1264,
        224
      ],
      "parameters": {
        "mode": "combine",
        "options": {},
        "combineBy": "combineByPosition",
        "numberInputs": 3
      },
      "typeVersion": 3
    },
    {
      "id": "36d98d38-5e6b-45eb-81cb-2821db5a950a",
      "name": "Finalize Data",
      "type": "n8n-nodes-base.code",
      "position": [
        1536,
        240
      ],
      "parameters": {
        "jsCode": "let result = {};\n\nfor (const i of items) {\n  result = { ...result, ...i.json };\n}\n\nreturn [{ json: result }];"
      },
      "typeVersion": 2
    },
    {
      "id": "765c05d9-2998-4942-9e78-d9066129cee9",
      "name": "Send Slack Summary",
      "type": "n8n-nodes-base.slack",
      "position": [
        1776,
        336
      ],
      "parameters": {
        "text": "=\ud83d\udcca *Daily Sales Snapshot*\n\n\ud83e\uddfe Orders: {{$json.orderCount}}\n\ud83d\udcb0 Revenue: {{$json.currency}} {{$json.totalRevenue}}\n\ud83d\udcc8 AOV: {{$json.currency}} {{$json.aov}}\n\n\ud83d\udd25 *Top Products*\n{{$json.topProducts.map(p => `\u2022 ${p[0]} (${p[1]})`).join('\\n')}}",
        "select": "channel",
        "channelId": {
          "__rl": true,
          "mode": "list",
          "value": "C0A3WQEKQ58",
          "cachedResultName": "n8n-demo"
        },
        "otherOptions": {}
      },
      "credentials": {
        "slackApi": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 2
    },
    {
      "id": "a7f2d14e-842b-45e5-8cda-dc539d260ecc",
      "name": "Append or update row in sheet",
      "type": "n8n-nodes-base.googleSheets",
      "position": [
        1760,
        112
      ],
      "parameters": {
        "columns": {
          "value": {
            "aov": "={{ $json.aov }}",
            "currency": "={{ $json.currency }}",
            "timezone": "={{ $json.Timezone }}",
            "timestamp": "={{ $json.timestamp }}",
            "orderCount": "={{ $json.orderCount }}",
            "topProducts": "={{ $json.topProducts }}",
            "totalRevenue": "={{ $json.totalRevenue }}"
          },
          "schema": [
            {
              "id": "topProducts",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "topProducts",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "totalRevenue",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "totalRevenue",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "orderCount",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "orderCount",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "aov",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "aov",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "currency",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "currency",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "timestamp",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "timestamp",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            },
            {
              "id": "timezone",
              "type": "string",
              "display": true,
              "removed": false,
              "required": false,
              "displayName": "timezone",
              "defaultMatch": false,
              "canBeUsedToMatch": true
            }
          ],
          "mappingMode": "defineBelow",
          "matchingColumns": [
            "timestamp"
          ],
          "attemptToConvertTypes": false,
          "convertFieldsToString": false
        },
        "options": {},
        "operation": "appendOrUpdate",
        "sheetName": {
          "__rl": true,
          "mode": "list",
          "value": "gid=0",
          "cachedResultUrl": "",
          "cachedResultName": "Sheet1"
        },
        "documentId": {
          "__rl": true,
          "mode": "list",
          "value": "1YNP9imIU1o1PkFFp0uXEmf4JdHsBd5X5gXW9_3FHSiQ",
          "cachedResultUrl": "",
          "cachedResultName": "Daily WooCommerce Sales Snapshot \u2192 Slack"
        }
      },
      "credentials": {
        "googleSheetsOAuth2Api": {
          "name": "<your credential>"
        }
      },
      "typeVersion": 4.7
    },
    {
      "id": "55e17d5d-f6be-438c-954b-9da5be78f927",
      "name": "Sticky Note",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -32,
        48
      ],
      "parameters": {
        "color": 7,
        "width": 304,
        "height": 480,
        "content": "## Daily Workflow Trigger\n\nStarts the workflow automatically each day using a Schedule Trigger.\nIt ensures daily sales data is collected, processed and reported\nconsistently without any manual intervention.\n"
      },
      "typeVersion": 1
    },
    {
      "id": "eb621894-23ea-479a-b891-5bf0ea41c154",
      "name": "Sticky Note1",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        320,
        48
      ],
      "parameters": {
        "color": 7,
        "width": 544,
        "height": 480,
        "content": "## Fetch & Filter Orders\nThis section fetches orders from WooCommerce, keeps only paid orders and filters them to include orders from the last 24 hours. This helps ensure that only valid and recent sales data is used for revenue calculation."
      },
      "typeVersion": 1
    },
    {
      "id": "a80064d1-b88c-44aa-92fd-653631eacda7",
      "name": "Sticky Note2",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        928,
        -160
      ],
      "parameters": {
        "color": 7,
        "width": 528,
        "height": 720,
        "content": "## Sales Metrics Calculation & Merge\n\nHere the workflow calculates key metrics using separate Code nodes:\n\u2022 Total Revenue\n\u2022 Order Count\n\u2022 Average Order Value (AOV)\n\u2022 Top Selling Products\n\nAll results are merged and normalized into a single object\nfor easy reuse in alerts, reports or future extensions."
      },
      "typeVersion": 1
    },
    {
      "id": "d3f2b0de-7c53-45cd-917d-8ec9902a9ac9",
      "name": "Sticky Note3",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        1536,
        -208
      ],
      "parameters": {
        "color": 7,
        "width": 528,
        "height": 768,
        "content": "## Sales Summary & Logging\n\nThis section sends a clean, human-readable sales summary to Slack\nand records the same data in Google Sheets.\n\nIncludes:\n\u2022 Total revenue\n\u2022 Number of orders\n\u2022 Average order value (AOV)\n\u2022 Top selling products\n\nSlack provides instant visibility into daily performance,\nwhile Google Sheets maintains a historical log for tracking\ntrends and reporting\u2014without logging into dashboards.\n"
      },
      "typeVersion": 1
    },
    {
      "id": "9f7a66c5-67a8-4823-a9f1-a1faebfb4b80",
      "name": "Sticky Note4",
      "type": "n8n-nodes-base.stickyNote",
      "position": [
        -688,
        -288
      ],
      "parameters": {
        "width": 560,
        "height": 1040,
        "content": "## How This Workflow Works\n\n1. The workflow runs automatically once every day using a Schedule Trigger (Cron).\n\n2. It fetches recent orders from WooCommerce as the source sales data.\n\n3. Only paid orders (Completed / Processing) are considered to ensure accurate reporting.\n\n4. Orders created within the last 24 hours are filtered using a Code node.\n\n5. Separate Code nodes calculate key sales metrics such as:\n   \u2022 Total Revenue\n   \u2022 Order Count\n   \u2022 Average Order Value (AOV)\n   \u2022 Top Selling Products\n\n6. All calculated metrics are merged and formatted into a single consolidated object.\n\n7. A clean and readable daily sales summary is sent to a Slack channel,\n   giving the team instant visibility into sales performance.\n\n8. The same sales data is also appended as a new row in Google Sheets,\n   creating a daily log for tracking trends and historical analysis.\n\n---\n\n## How to Set Up This Workflow\n\nAdd a Schedule Trigger to run the workflow daily.\n\nAdd a WooCommerce node to fetch all orders.\n\nFilter orders by Completed / Processing status.\n\nUse a Code node to keep only orders from the last 24 hours.\n\nAdd separate Code nodes to calculate revenue, order count, AOV and top products.\n\nUse a Merge node to combine all calculated metrics.\n\nAdd a final Code node to normalize the merged data into one object.\n\nConnect a Slack node to send the daily sales summary.\n\nConnect a Google Sheets node to append the daily metrics as a new row.\n\nTest the workflow and activate it.\n"
      },
      "typeVersion": 1
    }
  ],
  "active": false,
  "settings": {
    "executionOrder": "v1"
  },
  "versionId": "738e9f95-ae4a-4453-9c92-1d95dfef1997",
  "connections": {
    "Finalize Data": {
      "main": [
        [
          {
            "node": "Append or update row in sheet",
            "type": "main",
            "index": 0
          },
          {
            "node": "Send Slack Summary",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Merge Metrics": {
      "main": [
        [
          {
            "node": "Finalize Data",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Daily Schedule": {
      "main": [
        [
          {
            "node": "Fetch WooCommerce Orders",
            "type": "main",
            "index": 0
          },
          {
            "node": "Merge Metrics",
            "type": "main",
            "index": 2
          }
        ]
      ]
    },
    "Last 24h Orders": {
      "main": [
        [
          {
            "node": "Calculate Revenue + AOV",
            "type": "main",
            "index": 0
          },
          {
            "node": "Calculate Top Products",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Filter Paid Orders": {
      "main": [
        [
          {
            "node": "Last 24h Orders",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Calculate Top Products": {
      "main": [
        [
          {
            "node": "Merge Metrics",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Calculate Revenue + AOV": {
      "main": [
        [
          {
            "node": "Merge Metrics",
            "type": "main",
            "index": 1
          }
        ]
      ]
    },
    "Fetch WooCommerce Orders": {
      "main": [
        [
          {
            "node": "Filter Paid Orders",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Append or update row in sheet": {
      "main": [
        []
      ]
    }
  }
}