RichardVR commited on
Commit
81b8ab0
·
verified ·
1 Parent(s): 449ace5

Create workflow.py

Browse files
Files changed (1) hide show
  1. workflow.py +557 -0
workflow.py ADDED
@@ -0,0 +1,557 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import json
2
+ from typing import Dict, Any, Optional
3
+ import requests
4
+ import os
5
+ import time
6
+ # import gspread # TODO: Install with pip install gspread
7
+ # from slack_sdk import WebClient # TODO: Install with pip install slack-sdk
8
+ import smtplib
9
+ from email.mime.text import MIMEText
10
+ from email.mime.multipart import MIMEMultipart
11
+
12
+ def main():
13
+ '''
14
+ Converted n8n workflow to Python script
15
+ Generated automatically from n8n workflow using n8n2py
16
+
17
+ This script contains the core logic from your n8n workflow.
18
+ Some nodes may require additional setup or API keys.
19
+ '''
20
+ try:
21
+
22
+ # TODO: Unknown node type: n8n-nodes-base.stickyNote
23
+ # Node: Sticky Note
24
+ # This node type is not recognized by n8n2py
25
+ # Parameters: {
26
+ "content": "# Research Daily News and Write Script",
27
+ "height": 2100,
28
+ "width": 940,
29
+ "color": 2
30
+ }
31
+ #
32
+ # To implement this node:
33
+ # 1. Research the node's functionality in n8n documentation
34
+ # 2. Find appropriate Python libraries for the same functionality
35
+ # 3. Add implementation to nodeHandlers.ts
36
+ # 4. Test the conversion
37
+
38
+ print(f"⚠️ Skipping unknown node: Sticky Note ({node.type})")
39
+
40
+
41
+ # TODO: Unknown node type: n8n-nodes-base.stickyNote
42
+ # Node: Sticky Note1
43
+ # This node type is not recognized by n8n2py
44
+ # Parameters: {
45
+ "content": "# Create AI Avatar Video\n\n- Heygen API plan (paid) is required; the free plan is insufficient.\n- if you have a long script, you may need to increase the WAIT time.\n- you can use Elevenlabs voice by integrating Elevenlabs from within Heygen app.",
46
+ "height": 2100,
47
+ "width": 800,
48
+ "color": 3
49
+ }
50
+ #
51
+ # To implement this node:
52
+ # 1. Research the node's functionality in n8n documentation
53
+ # 2. Find appropriate Python libraries for the same functionality
54
+ # 3. Add implementation to nodeHandlers.ts
55
+ # 4. Test the conversion
56
+
57
+ print(f"⚠️ Skipping unknown node: Sticky Note1 ({node.type})")
58
+
59
+
60
+ # TODO: Unknown node type: n8n-nodes-base.stickyNote
61
+ # Node: Sticky Note2
62
+ # This node type is not recognized by n8n2py
63
+ # Parameters: {
64
+ "content": "# Publish to Social Media\n\n- Sign up for Blotato: https://www.blotato.com\n- Blotato's API currently doesn't support uploading videos to Bluesky or Pinterest. \n- This feature will be released in the future, so I've deactivated the nodes for now.",
65
+ "height": 2100,
66
+ "width": 1120,
67
+ "color": 4
68
+ }
69
+ #
70
+ # To implement this node:
71
+ # 1. Research the node's functionality in n8n documentation
72
+ # 2. Find appropriate Python libraries for the same functionality
73
+ # 3. Add implementation to nodeHandlers.ts
74
+ # 4. Test the conversion
75
+
76
+ print(f"⚠️ Skipping unknown node: Sticky Note2 ({node.type})")
77
+
78
+
79
+ # HTTP Request: [Instagram] Publish via Blotato
80
+ headers = {"Content-Type": "application/json"}
81
+
82
+ instagram_publish_via_blotato_response = requests.post(
83
+ url="https://backend.blotato.com/v2/posts",
84
+ headers=headers
85
+ )
86
+
87
+ # Handle response
88
+ if instagram_publish_via_blotato_response.status_code == 200:
89
+ instagram_publish_via_blotato_data = instagram_publish_via_blotato_response.json()
90
+ print(f"✅ [Instagram] Publish via Blotato successful: {instagram_publish_via_blotato_response.status_code}")
91
+ else:
92
+ print(f"❌ [Instagram] Publish via Blotato failed: {instagram_publish_via_blotato_response.status_code}")
93
+ instagram_publish_via_blotato_data = None
94
+
95
+
96
+ # HTTP Request: [Youtube] Publish via Blotato
97
+ headers = {"Content-Type": "application/json"}
98
+
99
+ youtube_publish_via_blotato_response = requests.post(
100
+ url="https://backend.blotato.com/v2/posts",
101
+ headers=headers
102
+ )
103
+
104
+ # Handle response
105
+ if youtube_publish_via_blotato_response.status_code == 200:
106
+ youtube_publish_via_blotato_data = youtube_publish_via_blotato_response.json()
107
+ print(f"✅ [Youtube] Publish via Blotato successful: {youtube_publish_via_blotato_response.status_code}")
108
+ else:
109
+ print(f"❌ [Youtube] Publish via Blotato failed: {youtube_publish_via_blotato_response.status_code}")
110
+ youtube_publish_via_blotato_data = None
111
+
112
+
113
+ # HTTP Request: [Facebook] Publish via Blotato
114
+ headers = {"Content-Type": "application/json"}
115
+
116
+ facebook_publish_via_blotato_response = requests.post(
117
+ url="https://backend.blotato.com/v2/posts",
118
+ headers=headers
119
+ )
120
+
121
+ # Handle response
122
+ if facebook_publish_via_blotato_response.status_code == 200:
123
+ facebook_publish_via_blotato_data = facebook_publish_via_blotato_response.json()
124
+ print(f"✅ [Facebook] Publish via Blotato successful: {facebook_publish_via_blotato_response.status_code}")
125
+ else:
126
+ print(f"❌ [Facebook] Publish via Blotato failed: {facebook_publish_via_blotato_response.status_code}")
127
+ facebook_publish_via_blotato_data = None
128
+
129
+
130
+ # HTTP Request: [Threads] Publish via Blotato
131
+ headers = {"Content-Type": "application/json"}
132
+
133
+ threads_publish_via_blotato_response = requests.post(
134
+ url="https://backend.blotato.com/v2/posts",
135
+ headers=headers
136
+ )
137
+
138
+ # Handle response
139
+ if threads_publish_via_blotato_response.status_code == 200:
140
+ threads_publish_via_blotato_data = threads_publish_via_blotato_response.json()
141
+ print(f"✅ [Threads] Publish via Blotato successful: {threads_publish_via_blotato_response.status_code}")
142
+ else:
143
+ print(f"❌ [Threads] Publish via Blotato failed: {threads_publish_via_blotato_response.status_code}")
144
+ threads_publish_via_blotato_data = None
145
+
146
+
147
+ # TODO: Unknown node type: @n8n/n8n-nodes-langchain.openAi
148
+ # Node: Write Long Caption
149
+ # This node type is not recognized by n8n2py
150
+ # Parameters: {
151
+ "modelId": {
152
+ "__rl": true,
153
+ "value": "gpt-4o",
154
+ "mode": "list",
155
+ "cachedResultName": "GPT-4O"
156
+ },
157
+ "messages": {
158
+ "values": [
159
+ {
160
+ "content": "=# EXAMPLE\n\n<example>\nMany people have recently asked me about ask engine optimization, which is all about optimizing your website and existing content, so it can be pulled into ChatGPT and other generative AI tools. Consider that generative AI tools tend to be more conversational in nature and have a Q&A type format, so search engines will want to pull in snippets that concisely answer a user’s question.- what is ask engine optimization in the age of AI?- How does traditional SEO compare to ask engine optimization today?- top tips and tricks to get started with ask engine optimization?\n\n#ai #askengineoptimization #chatgpts #seo #aitools #digitalmarketing\n</example>\n\n# CONTEXT\n\nInfer the topic from the sources provided.\n\n# WRITING STYLE\n\nHere’s how you always write:\n\n<writing_style>\n\n- Your writing style is spartan and informative.\n- Use clear, simple language.\n- Employ short, impactful sentences.\n- Use active voice; avoid passive voice.\n- Focus on practical, actionable insights.\n- Incorporate data or statistics to support claims when possible.\n- Use \"\"\"\"\"\"\"\"you\"\"\"\"\"\"\"\" and \"\"\"\"\"\"\"\"your\"\"\"\"\"\"\"\" to directly address the reader.\n- Avoid metaphors and clichés.\n- Avoid generalizations.\n- Do not include common setup language in any sentence, including: in conclusion, in closing, etc.\n- Do not output warnings or notes—just the output requested.\n- Do not use hashtags.\n- Do not use semicolons.\n- Do not use emojis.\n- Do not use asterisks.\n- Do not use adjectives and adverbs.\n- Do NOT use these words:\n\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"can, may, just, that, very, really, literally, actually, certainly, probably, basically, could, maybe, delve, embark, enlightening, esteemed, shed light, craft, crafting, imagine, realm, game-changer, unlock, discover, skyrocket, abyss, you're not alone, in a world where, revolutionize, disruptive, utilize, utilizing, dive deep, tapestry, illuminate, unveil, pivotal, enrich, intricate, elucidate, hence, furthermore, realm, however, harness, exciting, groundbreaking, cutting-edge, remarkable, it. remains to be seen, glimpse into, navigating, landscape, stark, testament, in summary, in conclusion, moreover, boost, bustling, opened up, powerful, inquiries, ever-evolving\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\"\n</writing_style>\n\n# PLANNING\n\nYour goal is to write a 50-word video caption based on the provided source.\n\n1. Analyze the provided sources thoroughly.\n2. Study the <example> post carefully. You will be asked to replicate their:\n - Overall structure.\n - Tone and voice.\n - Formatting (including line breaks and spacing).\n - Length (aim for a similarly detailed post).\n - Absence of emojis.\n - Use of hashtags.\n - Emotional resonance.\n\n# OUTPUT\nFollow the GUIDELINES below to write the post. Use your analysis from step 1 and step 2. Use the provided sources as the foundation for your post, expanding on it significantly while maintaining the style and structure of the examples provided from step 2. You MUST use information from the provided sources. Make sure you adhere to your <writing_style>.\n\n<guidelines>\nThe description should be structured as follows:\n1. Start with 1 paragraph summarizing the source\n2. Newline, followed by 3 bullet points of questions that a viewer might ask on a search engine about the source\n3. Newline, followed by these hashtags: #ai #artificialintelligence #ainews #sabrinaramonov #aiavatar\n</guidelines>\n\nTake a deep breath and take it step-by-step!\n\n# INPUT\nUse the following information sources:\n<sources>\n{{ $json.output }}\n</sources>"
161
+ }
162
+ ]
163
+ },
164
+ "options": {}
165
+ }
166
+ #
167
+ # To implement this node:
168
+ # 1. Research the node's functionality in n8n documentation
169
+ # 2. Find appropriate Python libraries for the same functionality
170
+ # 3. Add implementation to nodeHandlers.ts
171
+ # 4. Test the conversion
172
+
173
+ print(f"⚠️ Skipping unknown node: Write Long Caption ({node.type})")
174
+
175
+
176
+ # TODO: Unknown node type: n8n-nodes-base.scheduleTrigger
177
+ # Node: Schedule Trigger
178
+ # This node type is not recognized by n8n2py
179
+ # Parameters: {
180
+ "rule": {
181
+ "interval": [
182
+ {
183
+ "triggerAtHour": 10
184
+ }
185
+ ]
186
+ }
187
+ }
188
+ #
189
+ # To implement this node:
190
+ # 1. Research the node's functionality in n8n documentation
191
+ # 2. Find appropriate Python libraries for the same functionality
192
+ # 3. Add implementation to nodeHandlers.ts
193
+ # 4. Test the conversion
194
+
195
+ print(f"⚠️ Skipping unknown node: Schedule Trigger ({node.type})")
196
+
197
+
198
+ # TODO: Unknown node type: @n8n/n8n-nodes-langchain.agent
199
+ # Node: AI Agent
200
+ # This node type is not recognized by n8n2py
201
+ # Parameters: {
202
+ "promptType": "define",
203
+ "text": "# INSTRUCTIONS\n\nPerform the following tasks, in order:\n\n1. Fetch the top 10 stories from Hacker News from the past 24 hours related to AI or LLMs. \n\n2. Select the top story that is most likely to go viral on social media. \n\n3. Fetch the article and Hacker News comments.\n\n4. Create a 30-second monologue script for an AI avatar video, following these guidelines:\n - The script should be approximately 30 seconds when spoken aloud.\n - Include lots of details and statistics from the article.\n - Use 6th grade reading level.\n - Balanced viewpoint.\n - Script should be in single paragraph\n\n5. Update the script's first 2 sentences to use sensational viral hooks that grab the viewer's attention and spark curiosity. The 3rd sentence should start diving into the article's details.\n\n6. Replace the last sentence with: \"Hit follow to stay ahead in AI!\"\n\n# OUTPUT FORMAT\n\nONLY output the exact video script. Do not output anything else. NEVER include intermediate thoughts, notes, or formatting.\nR",
204
+ "options": {
205
+ "returnIntermediateSteps": true
206
+ }
207
+ }
208
+ #
209
+ # To implement this node:
210
+ # 1. Research the node's functionality in n8n documentation
211
+ # 2. Find appropriate Python libraries for the same functionality
212
+ # 3. Add implementation to nodeHandlers.ts
213
+ # 4. Test the conversion
214
+
215
+ print(f"⚠️ Skipping unknown node: AI Agent ({node.type})")
216
+
217
+
218
+ # Set Variables: Setup Heygen
219
+ # No variables to set
220
+
221
+
222
+ # HTTP Request: Create Avatar Video
223
+ base_url = os.getenv("HTTP_BASE_URL", "https://api.heygen.com/v2/video/generate")
224
+ headers = {"Content-Type": "application/json"}
225
+
226
+ create_avatar_video_response = requests.post(
227
+ url=base_url,
228
+ headers=headers
229
+ )
230
+
231
+ # Handle response
232
+ if create_avatar_video_response.status_code == 200:
233
+ create_avatar_video_data = create_avatar_video_response.json()
234
+ print(f"✅ Create Avatar Video successful: {create_avatar_video_response.status_code}")
235
+ else:
236
+ print(f"❌ Create Avatar Video failed: {create_avatar_video_response.status_code}")
237
+ create_avatar_video_data = None
238
+
239
+
240
+ # TODO: Unknown node type: n8n-nodes-base.wait
241
+ # Node: Wait
242
+ # This node type is not recognized by n8n2py
243
+ # Parameters: {
244
+ "amount": 8,
245
+ "unit": "minutes"
246
+ }
247
+ #
248
+ # To implement this node:
249
+ # 1. Research the node's functionality in n8n documentation
250
+ # 2. Find appropriate Python libraries for the same functionality
251
+ # 3. Add implementation to nodeHandlers.ts
252
+ # 4. Test the conversion
253
+
254
+ print(f"⚠️ Skipping unknown node: Wait ({node.type})")
255
+
256
+
257
+ # HTTP Request: Get Avatar Video
258
+ base_url = os.getenv("HTTP_BASE_URL", "https://api.heygen.com/v1/video_status.get")
259
+ headers = {"Content-Type": "application/json"}
260
+
261
+ get_avatar_video_response = requests.get(
262
+ url=base_url,
263
+ headers=headers
264
+ )
265
+
266
+ # Handle response
267
+ if get_avatar_video_response.status_code == 200:
268
+ get_avatar_video_data = get_avatar_video_response.json()
269
+ print(f"✅ Get Avatar Video successful: {get_avatar_video_response.status_code}")
270
+ else:
271
+ print(f"❌ Get Avatar Video failed: {get_avatar_video_response.status_code}")
272
+ get_avatar_video_data = None
273
+
274
+
275
+ # Set Variables: Prepare for Publish
276
+ # No variables to set
277
+
278
+
279
+ # HTTP Request: Upload to Blotato
280
+ headers = {"Content-Type": "application/json"}
281
+
282
+ upload_to_blotato_response = requests.post(
283
+ url="https://backend.blotato.com/v2/media",
284
+ headers=headers
285
+ )
286
+
287
+ # Handle response
288
+ if upload_to_blotato_response.status_code == 200:
289
+ upload_to_blotato_data = upload_to_blotato_response.json()
290
+ print(f"✅ Upload to Blotato successful: {upload_to_blotato_response.status_code}")
291
+ else:
292
+ print(f"❌ Upload to Blotato failed: {upload_to_blotato_response.status_code}")
293
+ upload_to_blotato_data = None
294
+
295
+
296
+ # HTTP Request: [Linkedin] Publish via Blotato
297
+ headers = {"Content-Type": "application/json"}
298
+
299
+ linkedin_publish_via_blotato_response = requests.post(
300
+ url="https://backend.blotato.com/v2/posts",
301
+ headers=headers
302
+ )
303
+
304
+ # Handle response
305
+ if linkedin_publish_via_blotato_response.status_code == 200:
306
+ linkedin_publish_via_blotato_data = linkedin_publish_via_blotato_response.json()
307
+ print(f"✅ [Linkedin] Publish via Blotato successful: {linkedin_publish_via_blotato_response.status_code}")
308
+ else:
309
+ print(f"❌ [Linkedin] Publish via Blotato failed: {linkedin_publish_via_blotato_response.status_code}")
310
+ linkedin_publish_via_blotato_data = None
311
+
312
+
313
+ # HTTP Request: [Twitter] Publish via Blotato
314
+ headers = {"Content-Type": "application/json"}
315
+
316
+ twitter_publish_via_blotato_response = requests.post(
317
+ url="https://backend.blotato.com/v2/posts",
318
+ headers=headers
319
+ )
320
+
321
+ # Handle response
322
+ if twitter_publish_via_blotato_response.status_code == 200:
323
+ twitter_publish_via_blotato_data = twitter_publish_via_blotato_response.json()
324
+ print(f"✅ [Twitter] Publish via Blotato successful: {twitter_publish_via_blotato_response.status_code}")
325
+ else:
326
+ print(f"❌ [Twitter] Publish via Blotato failed: {twitter_publish_via_blotato_response.status_code}")
327
+ twitter_publish_via_blotato_data = None
328
+
329
+
330
+ # TODO: Unknown node type: @n8n/n8n-nodes-langchain.openAi
331
+ # Node: Write Short Caption
332
+ # This node type is not recognized by n8n2py
333
+ # Parameters: {
334
+ "modelId": {
335
+ "__rl": true,
336
+ "value": "gpt-4o",
337
+ "mode": "list",
338
+ "cachedResultName": "GPT-4O"
339
+ },
340
+ "messages": {
341
+ "values": [
342
+ {
343
+ "content": "=Write a spartan 2-sentence caption summarizing the video content, use 6th grade language, balanced neutral perspective, no emojis:\n\n<content>\n{{ $json.message.content }}\n</content>"
344
+ }
345
+ ]
346
+ },
347
+ "options": {}
348
+ }
349
+ #
350
+ # To implement this node:
351
+ # 1. Research the node's functionality in n8n documentation
352
+ # 2. Find appropriate Python libraries for the same functionality
353
+ # 3. Add implementation to nodeHandlers.ts
354
+ # 4. Test the conversion
355
+
356
+ print(f"⚠️ Skipping unknown node: Write Short Caption ({node.type})")
357
+
358
+
359
+ # TODO: Unknown node type: n8n-nodes-base.stickyNote
360
+ # Node: Sticky Note3
361
+ # This node type is not recognized by n8n2py
362
+ # Parameters: {
363
+ "content": "## Make sure you fill out \"Setup Heygen\"",
364
+ "height": 180,
365
+ "width": 150,
366
+ "color": 6
367
+ }
368
+ #
369
+ # To implement this node:
370
+ # 1. Research the node's functionality in n8n documentation
371
+ # 2. Find appropriate Python libraries for the same functionality
372
+ # 3. Add implementation to nodeHandlers.ts
373
+ # 4. Test the conversion
374
+
375
+ print(f"⚠️ Skipping unknown node: Sticky Note3 ({node.type})")
376
+
377
+
378
+ # TODO: Unknown node type: n8n-nodes-base.stickyNote
379
+ # Node: Sticky Note4
380
+ # This node type is not recognized by n8n2py
381
+ # Parameters: {
382
+ "content": "## Make sure you fill out \"Prepare for Publish\"",
383
+ "height": 180,
384
+ "width": 160,
385
+ "color": 6
386
+ }
387
+ #
388
+ # To implement this node:
389
+ # 1. Research the node's functionality in n8n documentation
390
+ # 2. Find appropriate Python libraries for the same functionality
391
+ # 3. Add implementation to nodeHandlers.ts
392
+ # 4. Test the conversion
393
+
394
+ print(f"⚠️ Skipping unknown node: Sticky Note4 ({node.type})")
395
+
396
+
397
+ # TODO: Unknown node type: @n8n/n8n-nodes-langchain.lmChatOpenAi
398
+ # Node: Write Script
399
+ # This node type is not recognized by n8n2py
400
+ # Parameters: {
401
+ "model": {
402
+ "__rl": true,
403
+ "value": "gpt-4o-mini",
404
+ "mode": "list",
405
+ "cachedResultName": "gpt-4o-mini"
406
+ },
407
+ "options": {}
408
+ }
409
+ #
410
+ # To implement this node:
411
+ # 1. Research the node's functionality in n8n documentation
412
+ # 2. Find appropriate Python libraries for the same functionality
413
+ # 3. Add implementation to nodeHandlers.ts
414
+ # 4. Test the conversion
415
+
416
+ print(f"⚠️ Skipping unknown node: Write Script ({node.type})")
417
+
418
+
419
+ # TODO: Unknown node type: n8n-nodes-base.hackerNewsTool
420
+ # Node: Fetch HN Front Page
421
+ # This node type is not recognized by n8n2py
422
+ # Parameters: {
423
+ "resource": "all",
424
+ "additionalFields": {
425
+ "keyword": "AI",
426
+ "tags": [
427
+ "front_page"
428
+ ]
429
+ }
430
+ }
431
+ #
432
+ # To implement this node:
433
+ # 1. Research the node's functionality in n8n documentation
434
+ # 2. Find appropriate Python libraries for the same functionality
435
+ # 3. Add implementation to nodeHandlers.ts
436
+ # 4. Test the conversion
437
+
438
+ print(f"⚠️ Skipping unknown node: Fetch HN Front Page ({node.type})")
439
+
440
+
441
+ # TODO: Unknown node type: n8n-nodes-base.hackerNewsTool
442
+ # Node: Fetch HN Article
443
+ # This node type is not recognized by n8n2py
444
+ # Parameters: {
445
+ "articleId": "={{ /*n8n-auto-generated-fromAI-override*/ $fromAI('Article_ID', ``, 'string') }}",
446
+ "additionalFields": {
447
+ "includeComments": true
448
+ }
449
+ }
450
+ #
451
+ # To implement this node:
452
+ # 1. Research the node's functionality in n8n documentation
453
+ # 2. Find appropriate Python libraries for the same functionality
454
+ # 3. Add implementation to nodeHandlers.ts
455
+ # 4. Test the conversion
456
+
457
+ print(f"⚠️ Skipping unknown node: Fetch HN Article ({node.type})")
458
+
459
+
460
+ # HTTP Request: [Tiktok] Publish via Blotato
461
+ headers = {"Content-Type": "application/json"}
462
+
463
+ tiktok_publish_via_blotato_response = requests.post(
464
+ url="https://backend.blotato.com/v2/posts",
465
+ headers=headers
466
+ )
467
+
468
+ # Handle response
469
+ if tiktok_publish_via_blotato_response.status_code == 200:
470
+ tiktok_publish_via_blotato_data = tiktok_publish_via_blotato_response.json()
471
+ print(f"✅ [Tiktok] Publish via Blotato successful: {tiktok_publish_via_blotato_response.status_code}")
472
+ else:
473
+ print(f"❌ [Tiktok] Publish via Blotato failed: {tiktok_publish_via_blotato_response.status_code}")
474
+ tiktok_publish_via_blotato_data = None
475
+
476
+
477
+ # HTTP Request: [Bluesky] Publish via Blotato
478
+ headers = {"Content-Type": "application/json"}
479
+
480
+ bluesky_publish_via_blotato_response = requests.post(
481
+ url="https://backend.blotato.com/v2/posts",
482
+ headers=headers
483
+ )
484
+
485
+ # Handle response
486
+ if bluesky_publish_via_blotato_response.status_code == 200:
487
+ bluesky_publish_via_blotato_data = bluesky_publish_via_blotato_response.json()
488
+ print(f"✅ [Bluesky] Publish via Blotato successful: {bluesky_publish_via_blotato_response.status_code}")
489
+ else:
490
+ print(f"❌ [Bluesky] Publish via Blotato failed: {bluesky_publish_via_blotato_response.status_code}")
491
+ bluesky_publish_via_blotato_data = None
492
+
493
+
494
+ # TODO: Unknown node type: @n8n/n8n-nodes-langchain.openAi
495
+ # Node: OpenAI
496
+ # This node type is not recognized by n8n2py
497
+ # Parameters: {
498
+ "resource": "image",
499
+ "prompt": "={{ $('Prepare for Publish').item.json.final_text_long }}",
500
+ "options": {
501
+ "returnImageUrls": true
502
+ }
503
+ }
504
+ #
505
+ # To implement this node:
506
+ # 1. Research the node's functionality in n8n documentation
507
+ # 2. Find appropriate Python libraries for the same functionality
508
+ # 3. Add implementation to nodeHandlers.ts
509
+ # 4. Test the conversion
510
+
511
+ print(f"⚠️ Skipping unknown node: OpenAI ({node.type})")
512
+
513
+
514
+ # HTTP Request: Upload to Blotato - Image
515
+ headers = {"Content-Type": "application/json"}
516
+
517
+ upload_to_blotato_image_response = requests.post(
518
+ url="https://backend.blotato.com/v2/media",
519
+ headers=headers
520
+ )
521
+
522
+ # Handle response
523
+ if upload_to_blotato_image_response.status_code == 200:
524
+ upload_to_blotato_image_data = upload_to_blotato_image_response.json()
525
+ print(f"✅ Upload to Blotato - Image successful: {upload_to_blotato_image_response.status_code}")
526
+ else:
527
+ print(f"❌ Upload to Blotato - Image failed: {upload_to_blotato_image_response.status_code}")
528
+ upload_to_blotato_image_data = None
529
+
530
+
531
+ # HTTP Request: [Pinterest] Publish via Blotato
532
+ headers = {"Content-Type": "application/json"}
533
+
534
+ pinterest_publish_via_blotato_response = requests.post(
535
+ url="https://backend.blotato.com/v2/posts",
536
+ headers=headers
537
+ )
538
+
539
+ # Handle response
540
+ if pinterest_publish_via_blotato_response.status_code == 200:
541
+ pinterest_publish_via_blotato_data = pinterest_publish_via_blotato_response.json()
542
+ print(f"✅ [Pinterest] Publish via Blotato successful: {pinterest_publish_via_blotato_response.status_code}")
543
+ else:
544
+ print(f"❌ [Pinterest] Publish via Blotato failed: {pinterest_publish_via_blotato_response.status_code}")
545
+ pinterest_publish_via_blotato_data = None
546
+
547
+
548
+ print("✅ Workflow completed successfully!")
549
+
550
+ except Exception as e:
551
+ print(f"❌ Workflow failed: {str(e)}")
552
+ import traceback
553
+ traceback.print_exc()
554
+ raise
555
+
556
+ if __name__ == "__main__":
557
+ main()