AutomationFlowsSlack & Telegram › HomeLab

HomeLab

HomeLab. Uses scheduleTrigger, discord, ssh. Scheduled trigger; 8 nodes.

Cron / scheduled trigger★★★★☆ complexity8 nodesDiscordSsh
Slack & Telegram Trigger: Cron / scheduled Nodes: 8 Complexity: ★★★★☆

The workflow JSON

Copy or download the full n8n JSON below. Paste it into a new n8n workflow, add your credentials, activate. Full import guide →

Download .json
{
  "updatedAt": "2025-10-06T04:57:49.000Z",
  "createdAt": "2025-07-29T18:48:28.008Z",
  "id": "X5baTUVFHhvSO1SC",
  "name": "HomeLab",
  "active": true,
  "isArchived": false,
  "nodes": [
    {
      "parameters": {
        "rule": {
          "interval": [
            {}
          ]
        }
      },
      "type": "n8n-nodes-base.scheduleTrigger",
      "typeVersion": 1.2,
      "position": [
        -720,
        -288
      ],
      "id": "ab1cfe2d-a3d2-4f14-91ea-fc161b070951",
      "name": "Schedule Trigger"
    },
    {
      "parameters": {
        "authentication": "webhook",
        "content": "={{ $json.message }}",
        "options": {}
      },
      "type": "n8n-nodes-base.discord",
      "typeVersion": 2,
      "position": [
        -48,
        -288
      ],
      "id": "146421f7-1e45-486b-98a4-4deb773b9669",
      "name": "Discord",
      "credentials": {
        "discordWebhookApi": {
          "name": "<your credential>"
        }
      }
    },
    {
      "parameters": {
        "jsCode": "const output = $('update system').first().json.stdout\nlet message = \"\";\nlet status = \"\u2705\";\nconst logSnippet = output.slice(-1000);\nconst userId = \"664803448629493816\"; // Ganti dengan user Discord yang ingin ditag\nconst mention = `<@${userId}>`;\n\nif (output.toLowerCase().includes(\"error\") || output.toLowerCase().includes(\"failed\")) {\n  status = \"\u274c\";\n  message = `\\`\\`\\`\\n${logSnippet}\\n\\`\\`\\`\\n\u274c Update failed!\\n${mention}`;\n} else if (output.toLowerCase().includes(\"a reboot is required\")) {\n  status = \"\ud83d\udd04\";\n  message = `\\`\\`\\`\\n${logSnippet}\\n\\`\\`\\`\\n\ud83d\udd04 Update completed but reboot is required.\\n${mention}`;\n} else {\n  status = \"\u2705\";\n  message = `\\`\\`\\`\\n${logSnippet}\\n\\`\\`\\`\\n\u2705 System updated successfully!`;\n}\n\nreturn [{\n  json: {\n    status,\n    message\n  }\n}];\n"
      },
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        -272,
        -288
      ],
      "id": "d5808171-3559-4005-9116-b68f0adad9c8",
      "name": "Code"
    },
    {
      "parameters": {
        "authentication": "webhook",
        "content": "={{ $json.content }}\n-----------------------------------------",
        "options": {}
      },
      "type": "n8n-nodes-base.discord",
      "typeVersion": 2,
      "position": [
        -48,
        -64
      ],
      "id": "ba513429-2751-4051-b2d3-edf67c497de2",
      "name": "Discord1",
      "credentials": {
        "discordWebhookApi": {
          "name": "<your credential>"
        }
      }
    },
    {
      "parameters": {
        "jsCode": "const rawLog = $input.first().json.stdout;  // log input dari node sebelumnya\n\nconst updatedImages = [];\nconst failedImages = [];\n\nconst lines = rawLog.split(\"\\n\");\n\nfor (let i = 0; i < lines.length; i++) {\n  const line = lines[i].trim();\n\n  // Cek baris \"Pulling image\"\n  if (line.startsWith(\"[*] Pulling image:\")) {\n    const image = line.replace(\"[*] Pulling image: \", \"\").trim();\n    const statusLine = lines[i + 3] || \"\";  // Baris ke-3 setelah ini biasanya status\n    const errorLine = lines[i + 1] || \"\";   // Jika error, muncul setelah ini\n\n    if (statusLine.includes(\"Image is up to date\")) {\n      // Lewatkan (tidak perlu dicatat)\n    } else if (errorLine.includes(\"Error response from daemon\")) {\n      failedImages.push(`${image} \u274c`);\n    } else {\n      updatedImages.push(`${image} \u2705`);\n    }\n  }\n}\n\n// Format pesan\nconst startedAt = rawLog.match(/Started at (.+?) ===/i)?.[1] || \"Unknown\";\nconst completedAt = rawLog.match(/Completed at (.+?) ===/i)?.[1] || \"Unknown\";\n\nlet message = `\ud83d\udee0\ufe0f **Docker Auto Update Summary**\\n\\n`;\nmessage += `\ud83d\udd53 **Started**: ${startedAt}\\n\u2705 **Completed**: ${completedAt}\\n\\n`;\n\nif (updatedImages.length > 0) {\n  message += `\ud83d\udd04 **Updated Images:**\\n${updatedImages.map(i => `\u2022 ${i}`).join(\"\\n\")}\\n\\n`;\n}\n\nif (failedImages.length > 0) {\n  message += `\u2757 **Failed Pulls:**\\n${failedImages.map(i => `\u2022 ${i}`).join(\"\\n\")}\\n\\n`;\n}\n\nif (updatedImages.length === 0 && failedImages.length === 0) {\n  message += `\ud83d\udce6 All containers already up to date.\\n`;\n}\n\nreturn [\n  {\n    json: {\n      content: message  // Output ke Discord node\n    }\n  }\n];\n"
      },
      "type": "n8n-nodes-base.code",
      "typeVersion": 2,
      "position": [
        -272,
        -64
      ],
      "id": "2566227c-7ce0-498a-b457-bff46bf30732",
      "name": "Code1"
    },
    {
      "parameters": {
        "rule": {
          "interval": [
            {
              "triggerAtHour": 3
            }
          ]
        }
      },
      "type": "n8n-nodes-base.scheduleTrigger",
      "typeVersion": 1.2,
      "position": [
        -720,
        -64
      ],
      "id": "ddf8f63b-c2d1-4ac1-ac51-86d0760cfc1a",
      "name": "Schedule Trigger1"
    },
    {
      "parameters": {
        "command": "sudo nala update && sudo nala upgrade -y"
      },
      "type": "n8n-nodes-base.ssh",
      "typeVersion": 1,
      "position": [
        -496,
        -288
      ],
      "id": "683f5583-acd1-4443-9c9c-091509c29b68",
      "name": "update system",
      "credentials": {
        "sshPassword": {
          "name": "<your credential>"
        }
      }
    },
    {
      "parameters": {
        "command": "sudo ./autoupdate.sh",
        "cwd": "/home/n8nbot/dockerUpdate"
      },
      "type": "n8n-nodes-base.ssh",
      "typeVersion": 1,
      "position": [
        -496,
        -64
      ],
      "id": "38bb81de-883a-486d-8c34-8dc590a392bd",
      "name": "update docker",
      "credentials": {
        "sshPassword": {
          "name": "<your credential>"
        }
      }
    }
  ],
  "connections": {
    "Schedule Trigger": {
      "main": [
        [
          {
            "node": "update system",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Code": {
      "main": [
        [
          {
            "node": "Discord",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Code1": {
      "main": [
        [
          {
            "node": "Discord1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Schedule Trigger1": {
      "main": [
        [
          {
            "node": "update docker",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "update system": {
      "main": [
        [
          {
            "node": "Code",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "update docker": {
      "main": [
        [
          {
            "node": "Code1",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  },
  "settings": {
    "executionOrder": "v1",
    "callerPolicy": "workflowsFromSameOwner",
    "errorWorkflow": "AvhjGJdACMdnvIEn"
  },
  "staticData": {
    "node:Schedule Trigger": {
      "recurrenceRules": []
    },
    "node:Schedule Trigger1": {
      "recurrenceRules": []
    },
    "node:Metopen": {
      "recurrenceRules": []
    },
    "node:AI": {
      "recurrenceRules": []
    },
    "node:Informasi": {
      "recurrenceRules": []
    },
    "node:Jaringan": {
      "recurrenceRules": []
    },
    "node:Distribusi": {
      "recurrenceRules": []
    },
    "node:Embedded": {
      "recurrenceRules": []
    },
    "node:Sinyal": {
      "recurrenceRules": []
    },
    "node:Tatul": {
      "recurrenceRules": []
    },
    "node:prak distribusi": {
      "recurrenceRules": []
    },
    "node:PrakEmbedded": {
      "recurrenceRules": []
    }
  },
  "meta": {
    "templateCredsSetupCompleted": true
  },
  "versionId": "d1dced24-4b25-45dc-9e2e-3a376d75255f",
  "triggerCount": 2,
  "shared": [
    {
      "updatedAt": "2025-07-29T18:48:28.014Z",
      "createdAt": "2025-07-29T18:48:28.014Z",
      "role": "workflow:owner",
      "workflowId": "X5baTUVFHhvSO1SC",
      "projectId": "DiQC0tGxFhuiK9UM"
    }
  ],
  "tags": []
}

Credentials you'll need

Each integration node will prompt for credentials when you import. We strip credential IDs before publishing — you'll add your own.

About this workflow

HomeLab. Uses scheduleTrigger, discord, ssh. Scheduled trigger; 8 nodes.

Source: https://github.com/SamVivan1/n8n-Workflows-Backup/blob/main/homelab-X5baTUVFHhvSO1SC.json — original creator credit. Request a take-down →

More Slack & Telegram workflows → · Browse all categories →