n8nワークフローをOneDriveにバックアップ
上級
これはDevOps分野の自動化ワークフローで、29個のノードを含みます。主にN8n, Code, Merge, Switch, ConvertToFileなどのノードを使用。 n8n workflowをOneDriveへ自動バックアップし、クリーンアップとメール通知機能付き
前提条件
- •特別な前提条件なし、インポートしてすぐに使用可能
使用ノード (29)
カテゴリー
ワークフロープレビュー
ノード接続関係を可視化、ズームとパンをサポート
ワークフローをエクスポート
以下のJSON設定をn8nにインポートして、このワークフローを使用できます
{
"id": "k0dRcFrfMvlaqhT0",
"meta": {
"instanceId": "89249a8a187ba6e01e16112a0d334a3aa01d510ad8f88d223e12cc0a2a8beb6b"
},
"name": "Backup n8n workflows to Onedrive",
"tags": [],
"nodes": [
{
"id": "96aee703-bbf4-4de0-b6fb-7cf8428d5027",
"name": "ワークフローの取得",
"type": "n8n-nodes-base.n8n",
"position": [
-4592,
96
],
"parameters": {
"filters": {},
"requestOptions": {}
},
"typeVersion": 1
},
{
"id": "84b64870-e3c4-4762-9931-c5ec929c904e",
"name": "バックアップフォルダの取得",
"type": "n8n-nodes-base.microsoftOneDrive",
"position": [
-3248,
96
],
"parameters": {
"resource": "folder"
},
"typeVersion": 1
},
{
"id": "cf46cd5f-f000-40ec-a6c8-110984437c6c",
"name": "古いバックアップフォルダの削除",
"type": "n8n-nodes-base.microsoftOneDrive",
"position": [
-1344,
224
],
"parameters": {
"folderId": "={{ $json.id }}\n\n",
"resource": "folder",
"operation": "delete"
},
"typeVersion": 1,
"alwaysOutputData": false
},
{
"id": "c79f2638-dd31-4c07-ad61-b25efc2919bd",
"name": "HTMLメールの準備",
"type": "n8n-nodes-base.code",
"position": [
-480,
112
],
"parameters": {
"jsCode": "// Prepare backup success email data - SAFE for any flow path\nconst backupDate = DateTime.now();\n\n// SAFE: Get folder name - always available\nlet folderName = 'Unknown';\ntry {\n folderName = $('Create new backup folder').item.json.name;\n} catch (e) {\n console.log('Could not get folder name:', e.message);\n folderName = `n8n.backup Daily ${backupDate.toFormat('yyyy-MM-dd')}`;\n}\n\n// SAFE: Get original workflow data - always available\nlet originalWorkflowData = [];\nlet totalWorkflows = 0;\ntry {\n originalWorkflowData = $('Retrieve workflows').all();\n totalWorkflows = originalWorkflowData.length;\n} catch (e) {\n console.log('Could not get workflow data:', e.message);\n}\n\n// SAFE: Get uploaded files data - always available from input\nlet uploadedFiles = [];\ntry {\n uploadedFiles = $('Upload JSON to folder').all();\n} catch (e) {\n console.log('Could not get uploaded files:', e.message);\n // Fallback: try to get from current input if this is from Upload path\n try {\n uploadedFiles = $input.all();\n } catch (e2) {\n console.log('Could not get input data either:', e2.message);\n }\n}\n\n// Calculate statistics\nconst activeWorkflows = originalWorkflowData.filter(item => {\n return item.json && item.json.active === true;\n}).length;\nconst inactiveWorkflows = totalWorkflows - activeWorkflows;\n\n// Calculate total size from uploaded files\nconst totalSizeKB = uploadedFiles.reduce((sum, item) => {\n return sum + ((item.json && item.json.size) ? item.json.size : 0);\n}, 0) / 1024;\n\n// Enhanced workflow analysis\nconst workflowsByStatus = {\n active: [],\n inactive: [],\n recentlyModified: [],\n large: []\n};\n\n// Prepare workflow list\nconst workflowList = originalWorkflowData.map(item => {\n let lastUpdated = 'Unknown';\n let lastUpdatedDate = null;\n let status = 'Inactive';\n \n // Handle date from original workflow data\n try {\n if (item.json.updatedAt) {\n const date = DateTime.fromISO(item.json.updatedAt);\n if (date.isValid) {\n lastUpdated = date.toFormat('dd/MM/yyyy HH:mm');\n lastUpdatedDate = date;\n }\n } else if (item.json.lastModifiedDateTime) {\n const date = DateTime.fromISO(item.json.lastModifiedDateTime);\n if (date.isValid) {\n lastUpdated = date.toFormat('dd/MM/yyyy HH:mm');\n lastUpdatedDate = date;\n }\n } else if (item.json.createdAt) {\n const date = DateTime.fromISO(item.json.createdAt);\n if (date.isValid) {\n lastUpdated = date.toFormat('dd/MM/yyyy HH:mm');\n lastUpdatedDate = date;\n }\n }\n } catch (error) {\n console.log('Date parsing error for workflow:', item.json.name, error);\n lastUpdated = 'Date unavailable';\n }\n \n // Use active status from original data\n if (item.json && item.json.active === true) {\n status = 'Active';\n }\n \n // Find corresponding uploaded file to get size\n const uploadedFile = uploadedFiles.find(uf => uf.json && uf.json.name === item.json.name);\n const fileSize = uploadedFile ? Math.round((uploadedFile.json.size || 0) / 1024 * 100) / 100 : 0;\n \n const workflow = {\n name: (item.json && item.json.name) ? item.json.name : 'Unnamed workflow',\n active: status === 'Active',\n updatedAt: lastUpdated,\n lastUpdatedDate: lastUpdatedDate,\n size: fileSize,\n id: (item.json && item.json.id) ? item.json.id : 'unknown'\n };\n \n // Categorize workflows for insights\n if (workflow.active) {\n workflowsByStatus.active.push(workflow);\n } else {\n workflowsByStatus.inactive.push(workflow);\n }\n \n // Check if recently modified (last 7 days)\n if (lastUpdatedDate && lastUpdatedDate > DateTime.now().minus({ days: 7 })) {\n workflowsByStatus.recentlyModified.push(workflow);\n }\n \n // Check if large workflow (>50KB)\n if (fileSize > 50) {\n workflowsByStatus.large.push(workflow);\n }\n \n return workflow;\n}).sort((a, b) => {\n // Sort by date - newest first (nulls/unknowns go to end)\n if (!a.lastUpdatedDate && !b.lastUpdatedDate) return 0;\n if (!a.lastUpdatedDate) return 1;\n if (!b.lastUpdatedDate) return -1;\n return b.lastUpdatedDate - a.lastUpdatedDate;\n});\n\n// Calculate additional insights\nconst recentlyModifiedCount = workflowsByStatus.recentlyModified.length;\nconst largeWorkflowsCount = workflowsByStatus.large.length;\nconst averageWorkflowSize = totalWorkflows > 0 ? Math.round((totalSizeKB / totalWorkflows) * 100) / 100 : 0;\n\n// FIXED: SAFE cleanup status detection - handles all possible flow paths\nlet cleanupStatus = 'Not Attempted';\nlet cleanupNote = 'Cleanup status could not be determined';\nlet cleanupIcon = '❓';\nlet cleanupColor = '#6b7280';\n\n// Try to determine cleanup status by checking which nodes were executed\ntry {\n // Method 1: Check if we came from Switch node path 1 (no cleanup needed)\n // This is determined by checking if we have Code node summary data\n const currentInput = $input.all();\n let codeNodeSummary = null;\n \n // Look for Code node summary in current input or previous nodes\n if (currentInput.length > 0 && currentInput[0].json && typeof currentInput[0].json.hasOldFolders !== 'undefined') {\n codeNodeSummary = currentInput[0].json;\n }\n \n if (codeNodeSummary) {\n if (!codeNodeSummary.hasOldFolders) {\n // Switch went to path 1 (no cleanup needed)\n cleanupStatus = 'Not Needed';\n cleanupNote = `No old backup folders found (checked ${codeNodeSummary.totalFoldersChecked || 0} folders)`;\n cleanupIcon = '✅';\n cleanupColor = '#22c55e';\n } else {\n // Switch went to path 0 (cleanup was needed), but we're now in success email\n // This means Delete was successful\n // FIXED: Count actual deleted folders from current input (from Loop Over Items)\n const deletedFoldersCount = currentInput.filter(item => item.json && item.json.id && item.json.name).length;\n cleanupStatus = 'Completed';\n cleanupNote = `Successfully cleaned up ${deletedFoldersCount} old backup folder${deletedFoldersCount > 1 ? 's' : ''}`;\n cleanupIcon = '✅';\n cleanupColor = '#22c55e';\n }\n } else {\n // Fallback: try to safely check other nodes\n try {\n // Try Code node directly (might be available)\n const codeResults = $('Filter backup folder').all();\n if (codeResults.length > 0 && codeResults[0].json) {\n const summary = codeResults[0].json;\n if (!summary.hasOldFolders) {\n cleanupStatus = 'Not Needed';\n cleanupNote = 'No old folders found';\n cleanupIcon = '✅';\n cleanupColor = '#22c55e';\n } else {\n // FIXED: Use the correct oldFoldersCount from Code node summary\n cleanupStatus = 'Completed'; \n cleanupNote = `Cleaned up ${summary.oldFoldersCount || 1} old folder${(summary.oldFoldersCount || 1) > 1 ? 's' : ''}`;\n cleanupIcon = '✅';\n cleanupColor = '#22c55e';\n }\n }\n } catch (e) {\n // Code node not accessible, use generic status\n cleanupStatus = 'Unknown';\n cleanupNote = 'Cleanup status could not be determined from current execution path';\n cleanupIcon = '❓';\n cleanupColor = '#6b7280';\n }\n }\n \n} catch (e) {\n console.log('Error determining cleanup status:', e);\n cleanupStatus = 'Unknown';\n cleanupNote = 'Error determining cleanup status: ' + e.message;\n cleanupIcon = '❓';\n cleanupColor = '#6b7280';\n}\n\n// Create beautiful enhanced HTML email\nconst htmlBody = `\n<!DOCTYPE html>\n<html>\n<head>\n <meta charset=\"UTF-8\">\n <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\">\n <title>n8n Backup Success</title>\n <style>\n body { font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif; margin: 0; padding: 20px; background-color: #f5f7fa; }\n .container { max-width: 900px; margin: 0 auto; background: white; border-radius: 12px; box-shadow: 0 4px 20px rgba(0,0,0,0.1); overflow: hidden; }\n .header { background: linear-gradient(135deg, #667eea 0%, #764ba2 100%); color: white; padding: 30px; text-align: center; }\n .header h1 { margin: 0; font-size: 32px; font-weight: 300; }\n .success-badge { background: #10b981; color: white; padding: 10px 20px; border-radius: 25px; display: inline-block; margin-top: 15px; font-weight: 600; font-size: 16px; }\n .content { padding: 35px; }\n .summary { background: #f8fafc; border-radius: 12px; padding: 25px; margin-bottom: 30px; }\n .stats-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(180px, 1fr)); gap: 20px; margin-bottom: 25px; }\n .stat-card { background: white; border: 1px solid #e5e7eb; border-radius: 10px; padding: 20px; text-align: center; transition: transform 0.2s; }\n .stat-card:hover { transform: translateY(-2px); box-shadow: 0 4px 12px rgba(0,0,0,0.1); }\n .stat-number { font-size: 28px; font-weight: bold; color: #374151; margin-bottom: 8px; }\n .stat-label { color: #6b7280; font-size: 14px; text-transform: uppercase; letter-spacing: 0.5px; }\n .stat-sublabel { color: #9ca3af; font-size: 12px; margin-top: 4px; }\n .insights-section { background: #eff6ff; border-radius: 12px; padding: 25px; margin-bottom: 30px; }\n .insight-item { background: white; border-radius: 8px; padding: 15px; margin-bottom: 10px; border-left: 4px solid #3b82f6; }\n .insight-item:last-child { margin-bottom: 0; }\n .workflows-table { width: 100%; border-collapse: collapse; margin-top: 20px; }\n .workflows-table th { background: #f9fafb; color: #374151; padding: 14px 12px; text-align: left; font-weight: 600; border-bottom: 2px solid #e5e7eb; font-size: 14px; }\n .workflows-table td { padding: 12px; border-bottom: 1px solid #f3f4f6; font-size: 14px; }\n .workflows-table tr:hover { background-color: #f9fafb; }\n .status-active { color: #10b981; font-weight: 600; }\n .status-inactive { color: #6b7280; }\n .size-large { color: #f59e0b; font-weight: 600; }\n .size-normal { color: #6b7280; }\n .footer { background: #f9fafb; padding: 25px 35px; color: #6b7280; font-size: 14px; text-align: center; }\n .folder-name { color: #4f46e5; font-weight: 600; }\n .backup-info { background: #eff6ff; border-left: 4px solid #3b82f6; padding: 20px; margin-bottom: 25px; border-radius: 0 8px 8px 0; }\n .cleanup-info { background: ${cleanupStatus === 'Failed' ? '#fee2e2' : cleanupStatus === 'Partially Completed' ? '#fef3c7' : cleanupStatus === 'Unknown' ? '#f3f4f6' : '#f0fdf4'}; border-left: 4px solid ${cleanupColor}; padding: 15px; margin-top: 15px; border-radius: 0 6px 6px 0; font-size: 14px; }\n @media (max-width: 600px) {\n .stats-grid { grid-template-columns: repeat(2, 1fr); }\n .container { margin: 10px; }\n .content { padding: 25px; }\n .workflows-table th, .workflows-table td { padding: 8px; font-size: 13px; }\n }\n </style>\n</head>\n<body>\n <div class=\"container\">\n <div class=\"header\">\n <h1>🛡️ n8n Backup Complete</h1>\n <div class=\"success-badge\">✅ BACKUP SUCCESSFUL</div>\n </div>\n \n <div class=\"content\">\n <div class=\"backup-info\">\n <strong>📁 Backup Folder:</strong> <span class=\"folder-name\">${folderName}</span><br>\n <strong>📅 Backup Date:</strong> ${backupDate.toFormat('DDDD')}<br>\n <strong>⏰ Backup Time:</strong> ${backupDate.toFormat('HH:mm:ss ZZZZ')}<br>\n <strong>🏢 Instance:</strong> n8n\n <div class=\"cleanup-info\">\n ${cleanupIcon} <strong>Cleanup Status:</strong> ${cleanupStatus}<br>\n <span style=\"font-size: 13px; color: #4b5563;\">${cleanupNote}</span>\n </div>\n </div>\n \n <div class=\"summary\">\n <h2 style=\"margin-top: 0; color: #374151; font-size: 24px; margin-bottom: 20px;\">📊 Backup Summary</h2>\n <div class=\"stats-grid\">\n <div class=\"stat-card\">\n <div class=\"stat-number\">${totalWorkflows}</div>\n <div class=\"stat-label\">Total Workflows</div>\n </div>\n <div class=\"stat-card\">\n <div class=\"stat-number\">${activeWorkflows}</div>\n <div class=\"stat-label\">Active Workflows</div>\n <div class=\"stat-sublabel\">${totalWorkflows > 0 ? Math.round((activeWorkflows/totalWorkflows)*100) : 0}% of total</div>\n </div>\n <div class=\"stat-card\">\n <div class=\"stat-number\">${inactiveWorkflows}</div>\n <div class=\"stat-label\">Inactive Workflows</div>\n <div class=\"stat-sublabel\">${totalWorkflows > 0 ? Math.round((inactiveWorkflows/totalWorkflows)*100) : 0}% of total</div>\n </div>\n <div class=\"stat-card\">\n <div class=\"stat-number\">${Math.round(totalSizeKB * 100) / 100} KB</div>\n <div class=\"stat-label\">Total Backup Size</div>\n <div class=\"stat-sublabel\">Avg: ${averageWorkflowSize} KB per workflow</div>\n </div>\n <div class=\"stat-card\">\n <div class=\"stat-number\" style=\"color: ${cleanupColor};\">${cleanupIcon}</div>\n <div class=\"stat-label\">Cleanup Status</div>\n <div class=\"stat-sublabel\">${cleanupStatus}</div>\n </div>\n ${recentlyModifiedCount > 0 ? `\n <div class=\"stat-card\">\n <div class=\"stat-number\">${recentlyModifiedCount}</div>\n <div class=\"stat-label\">Recently Modified</div>\n <div class=\"stat-sublabel\">Last 7 days</div>\n </div>\n ` : ''}\n ${largeWorkflowsCount > 0 ? `\n <div class=\"stat-card\">\n <div class=\"stat-number\">${largeWorkflowsCount}</div>\n <div class=\"stat-label\">Large Workflows</div>\n <div class=\"stat-sublabel\">> 50 KB</div>\n </div>\n ` : ''}\n </div>\n </div>\n \n ${recentlyModifiedCount > 0 || largeWorkflowsCount > 0 ? `\n <div class=\"insights-section\">\n <h3 style=\"margin-top: 0; color: #374151; font-size: 18px; margin-bottom: 15px;\">💡 Backup Insights</h3>\n ${recentlyModifiedCount > 0 ? `\n <div class=\"insight-item\">\n <strong>🔄 Recent Activity:</strong> ${recentlyModifiedCount} workflow${recentlyModifiedCount > 1 ? 's have' : ' has'} been modified in the last 7 days, indicating active development.\n </div>\n ` : ''}\n ${largeWorkflowsCount > 0 ? `\n <div class=\"insight-item\">\n <strong>📈 Large Workflows:</strong> ${largeWorkflowsCount} workflow${largeWorkflowsCount > 1 ? 's are' : ' is'} larger than 50KB, which may indicate complex automation processes.\n </div>\n ` : ''}\n ${activeWorkflows > 0 ? `\n <div class=\"insight-item\">\n <strong>⚡ Active Operations:</strong> ${activeWorkflows} active workflow${activeWorkflows > 1 ? 's are' : ' is'} currently running and processing data automatically.\n </div>\n ` : ''}\n </div>\n ` : ''}\n \n <h3 style=\"color: #374151; margin-bottom: 15px;\">📋 Backed Up Workflows</h3>\n <div style=\"overflow-x: auto;\">\n <table class=\"workflows-table\">\n <thead>\n <tr>\n <th>Workflow Name</th>\n <th>Status</th>\n <th>Last Updated</th>\n <th>Size (KB)</th>\n </tr>\n </thead>\n <tbody>\n ${workflowList.map(wf => `\n <tr>\n <td style=\"font-weight: 500;\">${wf.name}</td>\n <td class=\"${wf.active ? 'status-active' : 'status-inactive'}\">\n ${wf.active ? '🟢 Active' : '⚪ Inactive'}\n </td>\n <td>${wf.updatedAt}</td>\n <td class=\"${wf.size > 50 ? 'size-large' : 'size-normal'}\">\n ${wf.size} KB ${wf.size > 50 ? '📊' : ''}\n </td>\n </tr>\n `).join('')}\n </tbody>\n </table>\n </div>\n </div>\n \n <div class=\"footer\">\n <p style=\"margin-bottom: 10px;\">🚀 <strong>Automated backup by n8n</strong></p>\n <p style=\"margin-bottom: 10px;\">📅 Next backup scheduled for <strong>tomorrow at 01:00 AM</strong></p>\n <p style=\"margin-bottom: 10px;\">☁️ This backup has been safely stored in <strong>Microsoft OneDrive</strong></p>\n <p style=\"margin: 0; font-size: 12px; color: #9ca3af;\">\n Backup ID: ${folderName} | Generated: ${backupDate.toISO()}\n </p>\n </div>\n </div>\n</body>\n</html>\n`;\n\n// Debug logging\nconsole.log('Safe Email Debug Info:');\nconsole.log('Total workflows:', totalWorkflows);\nconsole.log('Active workflows:', activeWorkflows);\nconsole.log('Cleanup status:', cleanupStatus, '(' + cleanupNote + ')');\nconsole.log('Uploaded files:', uploadedFiles.length);\nconsole.log('Current input length:', $input.all().length);\n\nreturn [{\n json: {\n htmlEmailBody: htmlBody,\n subject: `🛡️ n8n Daily Backup Success - ${totalWorkflows} workflows backed up (${Math.round(totalSizeKB * 100) / 100} KB)`,\n summary: {\n totalWorkflows,\n activeWorkflows,\n inactiveWorkflows,\n totalSizeKB: Math.round(totalSizeKB * 100) / 100,\n averageWorkflowSize,\n recentlyModifiedCount,\n largeWorkflowsCount,\n backupDate: backupDate.toISO(),\n folderName,\n cleanupStatus,\n cleanupNote,\n cleanupIcon\n },\n workflowList,\n insights: {\n recentlyModified: workflowsByStatus.recentlyModified.length,\n largeWorkflows: workflowsByStatus.large.length,\n activePercentage: totalWorkflows > 0 ? Math.round((activeWorkflows/totalWorkflows)*100) : 0\n }\n }\n}];"
},
"typeVersion": 2
},
{
"id": "d846405f-6dde-40a1-b96f-e23225b59eb6",
"name": "日次スケジュールトリガー",
"type": "n8n-nodes-base.scheduleTrigger",
"position": [
-5520,
96
],
"parameters": {
"rule": {
"interval": [
{
"triggerAtHour": 1
}
]
}
},
"typeVersion": 1.2
},
{
"id": "7e961954-d2ed-4a9d-8725-d444a1868c9f",
"name": "HTML成功メールの送信",
"type": "n8n-nodes-base.microsoftOutlook",
"position": [
-80,
112
],
"webhookId": "cdac200b-7c74-455c-b68d-fda0885fac67",
"parameters": {
"subject": "={{ $json.subject }}",
"bodyContent": "={{ $json.htmlEmailBody }}",
"additionalFields": {
"bodyContentType": "html"
}
},
"typeVersion": 2
},
{
"id": "e7575c54-1134-45bc-a4ed-fe88d5d27634",
"name": "フォルダの検索",
"type": "n8n-nodes-base.microsoftOneDrive",
"disabled": true,
"position": [
-5216,
-272
],
"parameters": {
"query": "Daily",
"resource": "folder",
"operation": "search"
},
"typeVersion": 1
},
{
"id": "d9b6048b-49bb-4e6b-97e9-8fb0bd2b122a",
"name": "古いフォルダの切り替え",
"type": "n8n-nodes-base.switch",
"position": [
-2352,
96
],
"parameters": {
"rules": {
"values": [
{
"outputKey": "False",
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "4efc2685-d40a-4bcd-bb19-40a50cc80b13",
"operator": {
"type": "boolean",
"operation": "false",
"singleValue": true
},
"leftValue": "={{ $json.hasOldFolders }}",
"rightValue": ""
}
]
},
"renameOutput": true
},
{
"outputKey": "True",
"conditions": {
"options": {
"version": 2,
"leftValue": "",
"caseSensitive": true,
"typeValidation": "strict"
},
"combinator": "and",
"conditions": [
{
"id": "832f5561-39f3-4786-8842-0adc8071ecaa",
"operator": {
"type": "boolean",
"operation": "true",
"singleValue": true
},
"leftValue": "={{ $json.hasOldFolders }}",
"rightValue": ""
}
]
},
"renameOutput": true
}
]
},
"options": {}
},
"typeVersion": 3.2
},
{
"id": "df14e3ce-8a86-4c1d-a7a3-405f40f90d6b",
"name": "アイテムのループ処理",
"type": "n8n-nodes-base.splitInBatches",
"position": [
-1776,
240
],
"parameters": {
"options": {}
},
"typeVersion": 3
},
{
"id": "af00819c-d885-4021-b693-06b9fb102112",
"name": "マージ",
"type": "n8n-nodes-base.merge",
"position": [
-1008,
112
],
"parameters": {},
"typeVersion": 3.2
},
{
"id": "83e234c1-9eb7-48dc-8956-a818fa338a8f",
"name": "新しいバックアップフォルダの作成",
"type": "n8n-nodes-base.microsoftOneDrive",
"position": [
-5056,
96
],
"parameters": {
"name": "=n8n_{{$now.format('yyyy-MM-dd')}}",
"options": {
"parentFolderId": ""
},
"resource": "folder",
"operation": "create"
},
"typeVersion": 1
},
{
"id": "b1fda1d4-c8b6-4882-95a2-048400064677",
"name": "JSONファイルへの変換",
"type": "n8n-nodes-base.convertToFile",
"position": [
-4160,
96
],
"parameters": {
"mode": "each",
"options": {
"format": true,
"fileName": "={{ $json.name }}"
},
"operation": "toJson"
},
"typeVersion": 1.1
},
{
"id": "ea490d15-f4d0-485e-8686-deb9044012b6",
"name": "JSONのフォルダへのアップロード",
"type": "n8n-nodes-base.microsoftOneDrive",
"position": [
-3712,
96
],
"parameters": {
"parentId": "={{ $('Create new backup folder').item.json.id }}",
"binaryData": true
},
"retryOnFail": false,
"typeVersion": 1
},
{
"id": "21d3de22-1836-49cd-99b7-1fafb710294e",
"name": "バックアップフォルダのフィルタリング",
"type": "n8n-nodes-base.code",
"position": [
-2848,
96
],
"parameters": {
"jsCode": "// Filter backup folders older than 31 days - Clean version\nconst inputItems = $input.all();\nconst cutoffDate = DateTime.now().minus({ days: 31 });\n\nconsole.log('Filtering backup folders older than 31 days');\nconsole.log('Cutoff date:', cutoffDate.toISO());\nconsole.log('Total folders found:', inputItems.length);\n\n// Filter folders older than 8 days\nconst oldFolders = [];\n\n// Process each input item\ninputItems.forEach((item, index) => {\n try {\n if (item.json.lastModifiedDateTime) {\n const folderDate = DateTime.fromISO(item.json.lastModifiedDateTime);\n const isOld = folderDate < cutoffDate;\n \n console.log('Folder:', item.json.name || 'Unknown', 'Date:', folderDate.toFormat('dd/MM/yyyy'), 'Old:', isOld);\n \n if (isOld) {\n oldFolders.push(item);\n }\n }\n } catch (error) {\n console.log('Error parsing date for folder:', item.json.name, error);\n }\n});\n\nconsole.log('Old folders to delete:', oldFolders.length);\nconsole.log('Recent folders to keep:', inputItems.length - oldFolders.length);\n\nif (oldFolders.length > 0) {\n // FOUND OLD FOLDERS TO DELETE\n // Return ONLY the old folders with summary info in first item\n const result = oldFolders.map((folder, index) => {\n if (index === 0) {\n // First old folder gets summary metadata\n return {\n json: {\n id: folder.json.id,\n name: folder.json.name,\n lastModifiedDateTime: folder.json.lastModifiedDateTime,\n createdDateTime: folder.json.createdDateTime,\n size: folder.json.size,\n // Add metadata\n hasOldFolders: true,\n oldFoldersCount: oldFolders.length,\n totalFoldersChecked: inputItems.length,\n cutoffDate: cutoffDate.toISO()\n }\n };\n } else {\n // Other old folders keep original structure\n return {\n json: {\n id: folder.json.id,\n name: folder.json.name,\n lastModifiedDateTime: folder.json.lastModifiedDateTime,\n createdDateTime: folder.json.createdDateTime,\n size: folder.json.size\n }\n };\n }\n });\n \n console.log('Returning', result.length, 'OLD folders for deletion');\n return result;\n \n} else {\n // NO OLD FOLDERS FOUND\n // Return single summary item\n console.log('No old folders found - all folders are recent');\n return [{\n json: {\n hasOldFolders: false,\n oldFoldersCount: 0,\n totalFoldersChecked: inputItems.length,\n cutoffDate: cutoffDate.toISO(),\n recentFoldersCount: inputItems.length,\n message: 'All backup folders are recent - no cleanup needed'\n }\n }];\n}"
},
"typeVersion": 2
},
{
"id": "ba663fbc-67f2-47e3-a237-122aa555f7d8",
"name": "付箋 - 概要",
"type": "n8n-nodes-base.stickyNote",
"position": [
-6320,
128
],
"parameters": {
"color": 3,
"width": 600,
"height": 940,
"content": "## 🗂️ Automated Workflow Backup Manager\n\n### Goal:\nThis workflow automates the process of backing up your workflows in n8n by creating a new backup folder in OneDrive. It first retrieves existing workflows, deletes old backup folders if they exist, and then generates JSON files of the current workflows. An email notification confirms successful backups, ensuring you never lose your critical configurations.\n\n### How it works:\n- 🏁 **Schedule Trigger Daily**: Run the workflow daily.\n- 🔄 **Retrieve Workflows**: Use the n8n node to collect all of your workflows.\n- 💼 **Get Backup Folders**: Check for existing backup folders in OneDrive.\n- 🗑️ **Delete Old Folder**: Remove the previous backup if it exists.\n- 📧 **Prepare HTML Email**: Craft an email template to notify of successful backup.\n- 📤 **Send HTML Success Email**: Notify you upon successful execution.\n- 📁 **Create New Backup Folder**: Generate a new folder for the current backup.\n- 📝 **Convert to JSON**: Transform workflows into JSON format for storage.\n- 📤 **Upload JSON File**: Place the newly created JSON files into OneDrive.\n\n### Parameters to Configure:\n- OneDrive folder path for backups\n- Email address for notifications\n- Daily scheduling options\n\n### Limitations / Gotchas:\n- The workflow assumes an active OneDrive account.\n- Ensure that folder permissions allow file creation and deletion.\n- Sent A email using the Outlook Node\n\n### Expected Result:\nUpon execution, you'll receive a confirmation email, and the latest workflows will be securely backed up in the designated OneDrive folder.\n\n## The green notes need action.\n- For both you need to find the Folder ID. \n- Use the Search a Folder node to find the folder ID\n"
},
"typeVersion": 1
},
{
"id": "0a3c08c4-6a18-4755-be8d-fc45103959f0",
"name": "付箋 - HTML成功メールの送信",
"type": "n8n-nodes-base.stickyNote",
"position": [
-192,
304
],
"parameters": {
"color": 7,
"width": 380,
"height": 860,
"content": "## 📧 Send HTML Success Email \n\n### 🎯 Purpose\nSend an HTML formatted success email to a specified recipient, allowing for rich formatting and design in the email content.\n\n### 🔄 Inputs / Outputs\n- **Inputs:**\n - To: fill in your emailadres\n - Subject of the email (provided via `{{$json.subject}}`).\n - HTML content for the email body (provided via `{{$json.htmlEmailBody}}`).\n- **Outputs:**\n - Confirmation of the email sent or any errors encountered during the send process.\n\n### ⚙️ Key Fields to Configure\n- **To:** emailadress\n- **Subject:**\n - Set using `\"={{ $json.subject }}\"`.\n- **Body Content:**\n - Set using `\"={{ $json.htmlEmailBody }}\"`.\n- **Additional Fields:**\n - `bodyContentType`: Ensure it is set to `\"html\"` to properly render HTML content.\n\n### 📝 Tip / Validation\n- Verify that the `subject` and `htmlEmailBody` are populated before triggering the email to ensure that the recipient receives meaningful content.\n- Test the email format by sending a sample email to yourself to check for correct rendering of the HTML content."
},
"typeVersion": 1
},
{
"id": "46ee0eac-d1e0-4948-ad60-f729abe72f3c",
"name": "付箋 - HTMLメールの準備",
"type": "n8n-nodes-base.stickyNote",
"position": [
-608,
304
],
"parameters": {
"color": 7,
"width": 380,
"height": 860,
"content": "## 📧 Prepare HTML Email\n\n### 🎯 Purpose\nCreate a formatted HTML email to summarize and document the results of a successful backup process, including essential statistics and insights about workflows.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - Workflow data, including active and inactive workflows, and sizes of uploaded files.\n- **Outputs:**\n - An HTML formatted email body and a subject line for sending notifications about the backup.\n\n### ⚙️ Key Fields to Configure\n- **HTML Email Structure:** \n - The node builds a user-friendly email layout, including workflow statistics, insights, and cleanup status.\n- **Custom Variables in Email:**\n - Variables such as `totalWorkflows`, `activeWorkflows`, `cleanupStatus`, and `folderName` are used to populate the email dynamically.\n\n### 📝 Tip / Validation\n- Ensure that all previous nodes (like 'Retrieve workflows' and 'Upload JSON to folder') are executed successfully to provide accurate data for the email.\n- Test the email format to ensure it renders correctly across different email clients. \n- Monitor log outputs for debugging purposes, especially to check for potential data retrieval errors."
},
"typeVersion": 1
},
{
"id": "baec94aa-e4c1-4341-92aa-e787c084966e",
"name": "付箋 - マージ",
"type": "n8n-nodes-base.stickyNote",
"position": [
-1040,
304
],
"parameters": {
"color": 7,
"width": 380,
"height": 540,
"content": "## 🔗 Merge \n\n### 🎯 Purpose\nCombine multiple streams of data into a single output, allowing for flexible data manipulation and processing within workflows.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - Multiple data streams from preceding nodes.\n- **Outputs:** \n - A single combined data stream, merging inputs based on defined criteria.\n\n### 📝 Tip / Validation\n- Ensure that the inputs you want to merge are compatible in terms of data types and structure.\n- The Merge node can be configured to use different strategies (e.g., combine all inputs, take first input only). Double-check the merging strategy based on your workflow requirements."
},
"typeVersion": 1
},
{
"id": "7c8e9e6c-aa5e-4ecb-8669-f86051cce7ab",
"name": "付箋 - 古いバックアップフォルダの削除",
"type": "n8n-nodes-base.stickyNote",
"position": [
-1504,
448
],
"parameters": {
"color": 7,
"width": 380,
"height": 668,
"content": "## 🗑️ Delete Old Backup Folder \n\n### 🎯 Purpose\nRemove outdated backup folders from Microsoft OneDrive to maintain organization and free up space.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - Folder ID of the backup to be deleted, dynamically sourced from workflow data.\n- **Outputs:** \n - Confirmation of folder deletion, if applicable.\n\n### ⚙️ Key Fields to Configure\n- **Folder ID:** \n - Specify the ID of the folder you wish to delete. It should be passed dynamically using the expression `={{ $json.id }}`.\n\n### 📝 Tip / Validation\n- Ensure that the folder ID is correct to avoid accidental deletion of important data.\n- Confirm that adequate permissions are in place for the Microsoft OneDrive account being utilized to perform the delete operation.\n- Deleted folders cannot be recovered unless a backup system is in place; use this operation with caution."
},
"typeVersion": 1
},
{
"id": "c56f7762-dcfe-4078-ba90-2d14e9a05b31",
"name": "付箋 - アイテムのループ処理",
"type": "n8n-nodes-base.stickyNote",
"position": [
-1920,
448
],
"parameters": {
"color": 7,
"width": 380,
"height": 620,
"content": "## 📁 Loop Over Items \n\n### 🎯 Purpose\nRemove old folder 1 by 1\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - A list of items to be processed.\n- **Outputs:** \n - A series of batches, each containing a subset of the original items.\n\n### ⚙️ Key Fields to Configure\n- **Options:**\n - No specific options are specified, but batching may be adjusted by further custom configuration in connected nodes."
},
"typeVersion": 1
},
{
"id": "e4ccfaed-5fce-4b58-8757-f5883787b979",
"name": "付箋 - 古いフォルダの切り替え",
"type": "n8n-nodes-base.stickyNote",
"position": [
-2464,
272
],
"parameters": {
"color": 7,
"width": 380,
"height": 732,
"content": "## 🔄 Switch Old Folders \n\n### 🎯 Purpose\nThis node determines the presence of old folders and routes the workflow based on that condition.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - Boolean input `hasOldFolders` that indicates if old folders exist.\n- **Outputs:** \n - Two distinct outputs based on the conditions:\n - **True:** If `hasOldFolders` is true.\n - **False:** If `hasOldFolders` is false.\n\n### ⚙️ Key Fields to Configure\n- **Rules:**\n - Define conditions for routing:\n - **True Condition:** Triggered when `hasOldFolders` evaluates to true.\n - **False Condition:** Triggered when `hasOldFolders` evaluates to false.\n \n### 📝 Tip / Validation\n- Ensure the input `hasOldFolders` is correctly set to a boolean value (`true` or `false`).\n- Remember to define follow-up nodes for both output paths to manage workflow logic effectively. \n- Case sensitivity settings can be adjusted if necessary, but default options typically suffice for boolean operations."
},
"typeVersion": 1
},
{
"id": "8801d8ea-a8c3-4e5d-bc7b-4c5ecd0a9822",
"name": "付箋 - バックアップフォルダのフィルタリング",
"type": "n8n-nodes-base.stickyNote",
"position": [
-2976,
272
],
"parameters": {
"color": 7,
"width": 380,
"height": 876,
"content": "## 📁 Filter Backup Folder \n\n### 🎯 Purpose\nThis node filters and identifies backup folders that are older than 31 days, allowing for effective management and cleanup of dated backups.\n- Change the \"Days\" to keep the backups longer/shorter\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - A list of backup folders with associated metadata including `lastModifiedDateTime`.\n- **Outputs:** \n - Old backup folders for deletion or a summary message regarding folder age.\n\n### ⚙️ Key Fields to Configure\n- **inputItems:** \n - This receives folders with metadata such as `id`, `name`, `lastModifiedDateTime`, and `size`.\n \n### 📝 Tip / Validation\n- Ensure that the `lastModifiedDateTime` field is in ISO format for accurate date comparison.\n- The script will log the processing of each folder and can handle parsing errors without stopping the execution.\n- Check logs for details on filtered items, including summary information when old folders are found or when all folders are determined to be recent. \n\n### ⚠️ Gotchas\n- If no old folders are found, the output will include a message indicating that no cleanup is needed.\n- Modifications to the cutoff date can be made by adjusting the value in `DateTime.now().minus({ days: 31 })`."
},
"typeVersion": 1
},
{
"id": "8b871fe0-f8f4-48c1-9954-4ddb0a835293",
"name": "付箋 - バックアップフォルダの取得",
"type": "n8n-nodes-base.stickyNote",
"position": [
-3392,
272
],
"parameters": {
"color": 4,
"width": 380,
"height": 748,
"content": "## 📁 Get backup folders \n\n## Folder ID need the be insert \n\n### 🎯 Purpose\nRetrieve a list of backuped folders from your main backup folder to remove old backups folders.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - Use the folder ID that you get from the \"Search a folder \"Node\n- **Outputs:** \n - A list of backup folders stored in the connected OneDrive account.\n\n### ⚙️ Key Fields to Configure\n- **Resource:** \n - Set to `\"folder\"` to specify that you are querying for folder resources.\n\n### 📝 Tip / Validation\n- Ensure that your Microsoft OneDrive account credentials are correctly configured and authorized in n8n to avoid authentication errors.\n- Check the scope of access granted to the OneDrive API to ensure you have permissions to list folders."
},
"typeVersion": 1
},
{
"id": "05e566d8-2cf1-4d6a-ae96-8800a5ba3d43",
"name": "付箋 - JSONのフォルダへのアップロード",
"type": "n8n-nodes-base.stickyNote",
"position": [
-3824,
272
],
"parameters": {
"color": 7,
"width": 380,
"height": 876,
"content": "## 📁 Upload JSON to Folder \n\n### 🎯 Purpose\nUpload the JSON file(s) to newly create backup folder.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - JSON file data to be uploaded.\n - Parent folder ID where the JSON will be uploaded.\n- **Outputs:** \n - Confirmation of the uploaded file and its metadata.\n\n### ⚙️ Key Fields to Configure\n- **Parent ID:** \n - Set this to the ID of the folder where the JSON will be uploaded. It can be dynamically retrieved from another node, e.g., `={{ $('Create new backup folder').item.json.id }}`.\n- **Binary Data:** \n - Ensure this is set to true to properly upload binary JSON data.\n\n### 📝 Tip / Validation\n- Make sure the specified folder exists in OneDrive; the upload will fail if the folder is missing or inaccessible.\n- Verify that the OneDrive credentials used have sufficient permissions to upload files to the designated folder."
},
"typeVersion": 1
},
{
"id": "77768b3c-e607-4896-ba99-5f6ae71d40bc",
"name": "付箋 - JSONファイルへの変換",
"type": "n8n-nodes-base.stickyNote",
"position": [
-4288,
272
],
"parameters": {
"color": 7,
"width": 380,
"height": 876,
"content": "## 📄 Convert to JSON file \n\n### 🎯 Purpose\nConvert the workflows into a JSON file.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - Data to be formatted as JSON.\n- **Outputs:** \n - A JSON file generated based on the input data.\n\n### ⚙️ Key Fields to Configure\n- **Operation:** \n - Set to `toJson` (default).\n- **Mode:** \n - Specify `each` to convert each item individually.\n- **Options:**\n - **Format:** Set to `true` for pretty-printed JSON.\n - **File Name:** Use `={{ $json.name }}` to dynamically name the output file based on input data.\n"
},
"typeVersion": 1
},
{
"id": "a60decc9-42fc-465d-a89f-f552e6a84814",
"name": "付箋 - ワークフローの取得",
"type": "n8n-nodes-base.stickyNote",
"position": [
-4736,
272
],
"parameters": {
"color": 7,
"width": 380,
"height": 876,
"content": "## 📁 Retrieve Workflows \n\n### 🎯 Purpose\nFetch existing workflows from n8n, enabling users to review and document their configurations easily.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - No specific input parameters. Filters can be applied if needed.\n- **Outputs:** \n - List of workflows available in the n8n account for documentation purposes.\n\n### ⚙️ Key Fields to Configure\n- **Filters:** \n - Apply any specific criteria to limit the workflows retrieved. However, it is optional and can be left empty for a full list.\n- **Request Options:** \n - Adjust settings related to the request (though, no specific options are outlined in this case).\n\n### 📝 Tip / Validation\n- If using filters, ensure they are accurately defined to retrieve the desired workflows.\n- Regularly check your n8n account credentials to maintain access when retrieving workflows. Any disruption may result in access issues."
},
"typeVersion": 1
},
{
"id": "52972885-4bad-4a28-b02c-fd454d97a97f",
"name": "付箋 - フォルダの検索",
"type": "n8n-nodes-base.stickyNote",
"position": [
-5424,
-944
],
"parameters": {
"color": 2,
"width": 540,
"height": 860,
"content": "## 🔍 Search a Folder \n\n### 🎯 Purpose\nUse to find the Folder ID from your Backup folder, This folder will be used to create new daily folders \n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - **Query:** String to filter search results (e.g., \"Backup folder\").\n- **Outputs:** \n - List of folders that match the search criteria from Microsoft OneDrive.\n\n### ⚙️ Key Fields to Configure\n- **Resource:** \n - Set to \"folder\" to specify the type of resource you are searching for.\n- **Operation:** \n - Set to \"search\" to indicate the desired action.\n- **Query:** \n - Provide the search term for folder names (e.g., \"DBackup folder\").\n\n### 📝 Tip / Validation\n- Ensure that the Microsoft OneDrive credentials are correctly set up to allow access to the folder search functionality.\n- The node is currently **disabled**; enable it to search the folder ID\n- Consider potential limitations of the search functionality, such as case sensitivity or folder visibility settings."
},
"typeVersion": 1
},
{
"id": "cc5e9202-f9f3-4cac-a849-9d5f3febbf20",
"name": "付箋 - 新しいバックアップフォルダの作成",
"type": "n8n-nodes-base.stickyNote",
"position": [
-5184,
272
],
"parameters": {
"color": 4,
"width": 380,
"height": 924,
"content": "## 📁 Create New Backup Folder\n\n## Folder ID need the be insert \n\n### 🎯 Purpose\nCreate a new folder in Microsoft OneDrive specifically for backing up workflow documentation.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - Use the folder ID that you get from the \"Search a folder\"Node\n- **Outputs:** \n - New folder ID and details for further use or confirmation.\n\n### ⚙️ Key Fields to Configure\n- **Resource:** \n - Set to `\"folder\"` to specify the type of resource being created.\n- **Operation:** \n - Set to `\"create\"` to initiate the folder creation process.\n- **Name:** \n - Dynamic name generated as `n8n_{{current_date}}` where `current_date` is formatted as `yyyy-MM-dd`.\n- **Options:** \n - **parentFolderId:** \n - Leave blank if creating in the root directory or specify an existing folder ID if needed.\n\n### 📝 Tip / Validation\n- Ensure the Microsoft OneDrive account linked has appropriate permissions to create folders.\n- Verify the folder creation pattern aligns with your backup schedule and naming conventions for better organization."
},
"typeVersion": 1
},
{
"id": "ea1105b6-5b0e-4ee6-b1d0-a8f210cce50b",
"name": "付箋 - 日次スケジュールトリガー",
"type": "n8n-nodes-base.stickyNote",
"position": [
-5632,
272
],
"parameters": {
"color": 7,
"width": 380,
"height": 876,
"content": "## 📅 Schedule Trigger Daily \n\n### 🎯 Purpose\nTriggers the workflow daily at a specified time to ensure scheduled actions are automatically executed.\n\n### 🔄 Inputs / Outputs\n- **Inputs:** \n - None (This node operates based solely on its schedule).\n- **Outputs:** \n - A trigger signal that starts subsequent nodes in the workflow at the scheduled time.\n\n### ⚙️ Key Fields to Configure\n- **Trigger At Hour:** \n - Set to `1`, which means the workflow will be triggered daily at 1:00 AM.\n\n### 📝 Tip / Gotchas\n- Remember that the hour is based on the server's timezone settings—adjust accordingly if your workflow requires a different timezone.\n- If you need more complex scheduling (e.g., multiple trigger times), consider using additional nodes or configurations."
},
"typeVersion": 1
}
],
"active": false,
"pinData": {},
"settings": {
"executionOrder": "v1"
},
"versionId": "e5bb50a7-5d9c-42dd-b660-92172b5e49ae",
"connections": {
"af00819c-d885-4021-b693-06b9fb102112": {
"main": [
[
{
"node": "c79f2638-dd31-4c07-ad61-b25efc2919bd",
"type": "main",
"index": 0
}
]
]
},
"df14e3ce-8a86-4c1d-a7a3-405f40f90d6b": {
"main": [
[
{
"node": "af00819c-d885-4021-b693-06b9fb102112",
"type": "main",
"index": 1
}
],
[
{
"node": "cf46cd5f-f000-40ec-a6c8-110984437c6c",
"type": "main",
"index": 0
}
]
]
},
"84b64870-e3c4-4762-9931-c5ec929c904e": {
"main": [
[
{
"node": "21d3de22-1836-49cd-99b7-1fafb710294e",
"type": "main",
"index": 0
}
]
]
},
"c79f2638-dd31-4c07-ad61-b25efc2919bd": {
"main": [
[
{
"node": "7e961954-d2ed-4a9d-8725-d444a1868c9f",
"type": "main",
"index": 0
}
]
]
},
"96aee703-bbf4-4de0-b6fb-7cf8428d5027": {
"main": [
[
{
"node": "b1fda1d4-c8b6-4882-95a2-048400064677",
"type": "main",
"index": 0
}
]
]
},
"d9b6048b-49bb-4e6b-97e9-8fb0bd2b122a": {
"main": [
[
{
"node": "af00819c-d885-4021-b693-06b9fb102112",
"type": "main",
"index": 0
}
],
[
{
"node": "df14e3ce-8a86-4c1d-a7a3-405f40f90d6b",
"type": "main",
"index": 0
}
]
]
},
"b1fda1d4-c8b6-4882-95a2-048400064677": {
"main": [
[
{
"node": "ea490d15-f4d0-485e-8686-deb9044012b6",
"type": "main",
"index": 0
}
]
]
},
"21d3de22-1836-49cd-99b7-1fafb710294e": {
"main": [
[
{
"node": "d9b6048b-49bb-4e6b-97e9-8fb0bd2b122a",
"type": "main",
"index": 0
}
]
]
},
"ea490d15-f4d0-485e-8686-deb9044012b6": {
"main": [
[
{
"node": "84b64870-e3c4-4762-9931-c5ec929c904e",
"type": "main",
"index": 0
}
]
]
},
"d846405f-6dde-40a1-b96f-e23225b59eb6": {
"main": [
[
{
"node": "83e234c1-9eb7-48dc-8956-a818fa338a8f",
"type": "main",
"index": 0
}
]
]
},
"83e234c1-9eb7-48dc-8956-a818fa338a8f": {
"main": [
[
{
"node": "96aee703-bbf4-4de0-b6fb-7cf8428d5027",
"type": "main",
"index": 0
}
]
]
},
"cf46cd5f-f000-40ec-a6c8-110984437c6c": {
"main": [
[
{
"node": "df14e3ce-8a86-4c1d-a7a3-405f40f90d6b",
"type": "main",
"index": 0
}
]
]
}
}
}よくある質問
このワークフローの使い方は?
上記のJSON設定コードをコピーし、n8nインスタンスで新しいワークフローを作成して「JSONからインポート」を選択、設定を貼り付けて認証情報を必要に応じて変更してください。
このワークフローはどんな場面に適していますか?
上級 - DevOps
有料ですか?
このワークフローは完全無料です。ただし、ワークフローで使用するサードパーティサービス(OpenAI APIなど)は別途料金が発生する場合があります。
関連ワークフロー
n8n APIとメール送信を使用した週次ワークフローレポートの生成
n8n APIとメール送信を使って週次のワークフロー分析レポートを生成
N8n
Set
Code
+
N8n
Set
Code
19 ノードWessel Bulte
DevOps
高度な n8n ワークフローと GitHub の同期
GitHub による スマートな変更検出を使った ワークフロー バックアップの自動化
If
N8n
Set
+
If
N8n
Set
38 ノードMaksym Brashenko
DevOps
GitHub への自動化 n8n ワークフロー バックアップおよび削除の追跡
n8n のワーキングフローを GitHub へ自動バックアップし、削除を追跡
If
N8n
Set
+
If
N8n
Set
31 ノードMarcial Ambriz
DevOps
ワークフローを GitHub リポジトリに保存する
毎日のワークフロー バックアップを GitHub にアップロードし、Slack 通知を送信
If
N8n
Set
+
If
N8n
Set
18 ノードAndrew
DevOps
GitHub 同期ダッシュボード - V2
コミット履歴とロールバック機能を備えた GitHub ワークフロー バージョン管理ダッシュボード
If
N8n
Set
+
If
N8n
Set
94 ノードEduard
DevOps
オランダの公共採用情報をTenderNedで自動収集
オランダの公開請求データ収集を TenderNed で自動化
Xml
Code
Merge
+
Xml
Code
Merge
28 ノードWessel Bulte
市場調査
ワークフロー情報
難易度
上級
ノード数29
カテゴリー1
ノードタイプ10
作成者
Wessel Bulte
@uuesselCybersecurity and automation consultant specializing in n8n workflows for GDPR compliance, process optimization, and business integration. Helping teams streamline operations with secure, scalable automation solutions.
外部リンク
n8n.ioで表示 →
このワークフローを共有