{
  "name": "Monocrawl — YouTube uploads to Google Sheets",
  "nodes": [
    {
      "id": "youtube-uploads-to-sheets-manual-test",
      "name": "Manual test",
      "type": "n8n-nodes-base.manualTrigger",
      "typeVersion": 1,
      "position": [
        0,
        -100
      ],
      "parameters": {}
    },
    {
      "id": "youtube-uploads-to-sheets-daily-schedule",
      "name": "Daily schedule",
      "type": "n8n-nodes-base.scheduleTrigger",
      "typeVersion": 1.2,
      "position": [
        0,
        100
      ],
      "parameters": {
        "rule": {
          "interval": [
            {
              "field": "days",
              "daysInterval": 1,
              "triggerAtHour": 9
            }
          ]
        }
      }
    },
    {
      "id": "youtube-uploads-to-sheets-configure",
      "name": "Configure",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        220,
        0
      ],
      "parameters": {
        "jsCode": "const c = { baseUrl: 'https://www.monocrawl.com', channelUrl: 'REPLACE_CHANNEL_URL', spreadsheetId: 'REPLACE_SPREADSHEET_ID', sheet: 'Videos', maxResults: 25 };for(const v of Object.values(c))if(String(v).startsWith('REPLACE_'))throw Error('Fill in the settings in this Configure node before running.');return [{json:c}];"
      }
    },
    {
      "id": "youtube-uploads-to-sheets-get-data",
      "name": "Get data",
      "type": "n8n-nodes-base.httpRequest",
      "typeVersion": 4.2,
      "position": [
        450,
        0
      ],
      "parameters": {
        "method": "GET",
        "url": "={{ $('Configure').first().json.baseUrl + '/v1/youtube/channel/videos' }}",
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth",
        "sendQuery": true,
        "queryParameters": {
          "parameters": [
            {
              "name": "url",
              "value": "={{ $('Configure').first().json.channelUrl }}"
            },
            {
              "name": "max_results",
              "value": "={{ $('Configure').first().json.maxResults }}"
            }
          ]
        },
        "options": {
          "timeout": 60000,
          "response": {
            "response": {
              "responseFormat": "json"
            }
          }
        }
      }
    },
    {
      "id": "youtube-uploads-to-sheets-prepare-rows",
      "name": "Prepare rows",
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        680,
        0
      ],
      "parameters": {
        "jsCode": "const r=$input.first().json;if(r.success!==true)throw Error(r.error?.message||'Monocrawl request failed');if(r.synthetic||r.degraded||r.stale||r.data?._synthetic)throw Error('The API returned sample or stale fallback data. No destination was updated.');if(!Array.isArray(r.data?.items))throw Error('Expected a video list');\nreturn r.data.items.map(v=>{if(!v.id)throw Error('Video ID missing');return {json:{id:v.id,title:v.title??'',url:v.url??'',published_at:v.published_at??'',channel:v.channel?.name??v.channel?.title??'',observed_at:new Date().toISOString(),request_id:r.request_id??''}};});"
      }
    },
    {
      "id": "youtube-uploads-to-sheets-write-to-google-sheets",
      "name": "Write to Google Sheets",
      "type": "n8n-nodes-base.googleSheets",
      "typeVersion": 4.6,
      "position": [
        910,
        0
      ],
      "parameters": {
        "operation": "appendOrUpdate",
        "documentId": {
          "__rl": true,
          "value": "={{ $('Configure').first().json.spreadsheetId }}",
          "mode": "id"
        },
        "sheetName": {
          "__rl": true,
          "value": "={{ $('Configure').first().json.sheet }}",
          "mode": "name"
        },
        "columns": {
          "mappingMode": "autoMapInputData",
          "value": {},
          "matchingColumns": [
            "id"
          ],
          "schema": [
            {
              "id": "id",
              "displayName": "id",
              "required": false,
              "defaultMatch": true,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "title",
              "displayName": "title",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "url",
              "displayName": "url",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "published_at",
              "displayName": "published_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "channel",
              "displayName": "channel",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "observed_at",
              "displayName": "observed_at",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            },
            {
              "id": "request_id",
              "displayName": "request_id",
              "required": false,
              "defaultMatch": false,
              "display": true,
              "type": "string",
              "canBeUsedToMatch": true
            }
          ]
        },
        "options": {
          "cellFormat": "RAW"
        }
      }
    },
    {
      "id": "youtube-uploads-to-sheets-setup-notes",
      "name": "Setup notes",
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        260,
        -390
      ],
      "parameters": {
        "width": 680,
        "height": 290,
        "content": "# YouTube uploads to Google Sheets\n1. Edit Configure (source, destination and API base URL).\n2. Select a Header Auth credential on Get data: name x-api-key, value your Monocrawl key. Use a key from the same environment as baseUrl.\n3. Connect the Google Sheets credential and create a tab with these headers: id, title, url, published_at, channel, observed_at, request_id\n4. Run a manual test (charges for one API request; sends/writes real data), then publish to enable the daily schedule.\n\nRequests the newest 25 videos by default, without automatic pagination. A channel publishing more between checks can exceed this window.\n\nNo automatic request retry or pagination. See the request log for charges. Keep workflow concurrency at 1 for remembered state."
      }
    }
  ],
  "connections": {
    "Manual test": {
      "main": [
        [
          {
            "node": "Configure",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Daily schedule": {
      "main": [
        [
          {
            "node": "Configure",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Configure": {
      "main": [
        [
          {
            "node": "Get data",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Get data": {
      "main": [
        [
          {
            "node": "Prepare rows",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Prepare rows": {
      "main": [
        [
          {
            "node": "Write to Google Sheets",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  },
  "active": false,
  "settings": {
    "executionOrder": "v1",
    "timezone": "Europe/London"
  },
  "pinData": {},
  "tags": []
}
