Figma Integration [PARTLY CREATED]

Please add Figma to your integrations. Many use it to programmatically create designs so it will work well with your system.

Hi @TopDog. I’m Max and I head up product design at n8n. Figma is a great tool and I’d be interested to spec out what V1 functionality might look like. Could you provide some details on the types of things you’d want to do with it?

5 Likes

+1. Mainly Comment Sync, History Update Notification. So basically webhook support

https://www.figma.com/developers/api#webhooks_v2

I’ve been thinking more about Figma nodes. Seems like the Trigger would be more broadly useful than regular node (at least in terms of prioritizing releasing one), with coverage of the events @designedbyclu linked to in Figma webhook docs. @TopDog do you agree?

Also, please upvote this feature if you’d like it to be prioritized :slight_smile:

1 Like

Got created.

1 Like

Figma Trigger Node got released with [email protected]

2 Likes

Really excited that this is out! If you’re looking for any inspo on what to build first - I made a WF that will ping me on Mattermost if I allow a comment to be unresolved after 24 hours

Next up for this workflow

  • Filter by comments that only at-mention me
  • In adddition to marking comment as resolved, don’t send a ping to mattermost if I reply to their message

This would have been a nightmare for me to implement via scripting :rocket:

3 Likes

Hi @maxT I was wondering if you could share the workflow?

Sure thing! FYI, I’ve only so far worked on the happy path so have not yet considered error handling or weird edge cases. Nonetheless, hopefully it helps as a starting point @danielvianna

{
  "name": "Unanswered Figma comments > Mattermost",
  "nodes": [
    {
      "parameters": {},
      "name": "Start",
      "type": "n8n-nodes-base.start",
      "typeVersion": 1,
      "position": [
        -20,
        500
      ]
    },
    {
      "parameters": {
        "teamId": "855809802644660153",
        "triggerOn": "fileComment"
      },
      "name": "Figma Trigger (Beta)",
      "type": "n8n-nodes-base.figmaTrigger",
      "typeVersion": 1,
      "position": [
        460,
        300
      ],
      "webhookId": "3b035e61-c4e9-4ea7-907d-a4faada5f8ca",
      "credentials": {
        "figmaApi": {
          "id": "185",
          "name": "Figma account"
        }
      }
    },
    {
      "parameters": {
        "conditions": {
          "string": [
            {
              "value1": "={{$json[\"triggered_by\"][\"handle\"]}}",
              "value2": "Max Tkacz"
            }
          ]
        }
      },
      "name": "Posted by Max?",
      "type": "n8n-nodes-base.if",
      "typeVersion": 1,
      "position": [
        680,
        300
      ]
    },
    {
      "parameters": {},
      "name": "Posted by other user",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        940,
        420
      ]
    },
    {
      "parameters": {},
      "name": "Do nothing",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        940,
        200
      ]
    },
    {
      "parameters": {
        "amount": 5,
        "unit": "minutes"
      },
      "name": "Wait 23 hours",
      "type": "n8n-nodes-base.wait",
      "typeVersion": 1,
      "position": [
        1120,
        420
      ],
      "webhookId": "f247c08d-8363-4c41-afd3-adb1962319af"
    },
    {
      "parameters": {
        "authentication": "headerAuth",
        "url": "=https://api.figma.com/v1/files/{{$node[\"Figma Trigger (Beta)\"].json[\"file_key\"]}}/comments",
        "options": {
          "splitIntoItems": true
        }
      },
      "name": "Fetch Figma file's comments",
      "type": "n8n-nodes-base.httpRequest",
      "typeVersion": 1,
      "position": [
        740,
        760
      ],
      "notesInFlow": true,
      "credentials": {
        "httpHeaderAuth": {
          "id": "186",
          "name": "Max Figma"
        }
      },
      "notes": "Get updated status of all comments"
    },
    {
      "parameters": {
        "fieldToSplitOut": "comments",
        "options": {}
      },
      "name": "Split out comments",
      "type": "n8n-nodes-base.itemLists",
      "typeVersion": 1,
      "position": [
        940,
        760
      ],
      "notesInFlow": true,
      "notes": "So each comment is an item"
    },
    {
      "parameters": {
        "conditions": {
          "string": [
            {
              "value1": "={{$node[\"Figma Trigger (Beta)\"].json[\"comment_id\"]}}",
              "value2": "={{$json[\"id\"]}}"
            }
          ]
        }
      },
      "name": "Filter out other comments",
      "type": "n8n-nodes-base.if",
      "typeVersion": 1,
      "position": [
        1160,
        760
      ],
      "notesInFlow": true,
      "notes": "True = The trigger comment"
    },
    {
      "parameters": {
        "conditions": {
          "string": [
            {
              "value1": "={{$json[\"resolved_at\"]}}",
              "operation": "isEmpty"
            }
          ],
          "boolean": []
        }
      },
      "name": "Comment not resolved?",
      "type": "n8n-nodes-base.if",
      "typeVersion": 1,
      "position": [
        1420,
        680
      ],
      "notesInFlow": true,
      "notes": "True = not resolved"
    },
    {
      "parameters": {},
      "name": "Comment resolved after 23hrs",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        1660,
        780
      ]
    },
    {
      "parameters": {},
      "name": "Replace me (Send message somewhere)",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        1660,
        520
      ]
    }
  ],
  "connections": {
    "Figma Trigger (Beta)": {
      "main": [
        [
          {
            "node": "Posted by Max?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Posted by Max?": {
      "main": [
        [
          {
            "node": "Do nothing",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Posted by other user",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Posted by other user": {
      "main": [
        [
          {
            "node": "Wait 23 hours",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Fetch Figma file's comments": {
      "main": [
        [
          {
            "node": "Split out comments",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Split out comments": {
      "main": [
        [
          {
            "node": "Filter out other comments",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Filter out other comments": {
      "main": [
        [
          {
            "node": "Comment not resolved?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Comment not resolved?": {
      "main": [
        [
          {
            "node": "Replace me (Send message somewhere)",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Comment resolved after 23hrs",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Wait 23 hours": {
      "main": [
        [
          {
            "node": "Fetch Figma file's comments",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  },
  "active": true,
  "settings": {},
  "id": 1126
}

Thanks a lot!
I was wondering if you could check those?
I’m trying to similar but something is off:

{
  "nodes": [
    {
      "parameters": {
        "teamId": "957446306466020666",
        "triggerOn": "fileComment"
      },
      "name": "Figma Trigger (Beta)",
      "type": "n8n-nodes-base.figmaTrigger",
      "typeVersion": 1,
      "position": [
        120,
        740
      ],
      "webhookId": "3b035e61-c4e9-4ea7-907d-a4faada5f8ca",
      "credentials": {
        "figmaApi": {
          "id": "2",
          "name": "Figma account"
        }
      }
    },
    {
      "parameters": {
        "conditions": {
          "string": [
            {
              "value1": "={{$json[\"triggered_by\"][\"handle\"]}}",
              "value2": "Max Tkacz"
            }
          ]
        }
      },
      "name": "Posted by Max?",
      "type": "n8n-nodes-base.if",
      "typeVersion": 1,
      "position": [
        320,
        740
      ]
    },
    {
      "parameters": {},
      "name": "Posted by other user",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        580,
        860
      ]
    },
    {
      "parameters": {},
      "name": "Do nothing",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        580,
        640
      ]
    },
    {
      "parameters": {
        "amount": 0,
        "unit": "minutes"
      },
      "name": "Wait 23 hours",
      "type": "n8n-nodes-base.wait",
      "typeVersion": 1,
      "position": [
        760,
        860
      ],
      "webhookId": "f247c08d-8363-4c41-afd3-adb1962319af"
    },
    {
      "parameters": {
        "authentication": "headerAuth",
        "url": "=https://api.figma.com/v1/files/{{$node[\"Figma Trigger (Beta)\"].json[\"file_key\"]}}/comments",
        "options": {
          "splitIntoItems": true
        }
      },
      "name": "Fetch Figma file's comments",
      "type": "n8n-nodes-base.httpRequest",
      "typeVersion": 1,
      "position": [
        380,
        1200
      ],
      "notesInFlow": true,
      "credentials": {
        "httpHeaderAuth": {
          "id": "186",
          "name": "Max Figma"
        }
      },
      "notes": "Get updated status of all comments"
    },
    {
      "parameters": {
        "fieldToSplitOut": "comments",
        "options": {}
      },
      "name": "Split out comments",
      "type": "n8n-nodes-base.itemLists",
      "typeVersion": 1,
      "position": [
        580,
        1200
      ],
      "notesInFlow": true,
      "notes": "So each comment is an item"
    },
    {
      "parameters": {
        "conditions": {
          "string": [
            {
              "value1": "={{$node[\"Figma Trigger (Beta)\"].json[\"comment_id\"]}}",
              "value2": "={{$json[\"id\"]}}"
            }
          ]
        }
      },
      "name": "Filter out other comments",
      "type": "n8n-nodes-base.if",
      "typeVersion": 1,
      "position": [
        800,
        1200
      ],
      "notesInFlow": true,
      "notes": "True = The trigger comment"
    },
    {
      "parameters": {
        "conditions": {
          "string": [
            {
              "value1": "={{$json[\"resolved_at\"]}}",
              "operation": "isEmpty"
            }
          ],
          "boolean": []
        }
      },
      "name": "Comment not resolved?",
      "type": "n8n-nodes-base.if",
      "typeVersion": 1,
      "position": [
        1060,
        1120
      ],
      "notesInFlow": true,
      "notes": "True = not resolved"
    },
    {
      "parameters": {},
      "name": "Comment resolved after 23hrs",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        1300,
        1220
      ]
    },
    {
      "parameters": {},
      "name": "Replace me (Send message somewhere)",
      "type": "n8n-nodes-base.noOp",
      "typeVersion": 1,
      "position": [
        1300,
        960
      ]
    }
  ],
  "connections": {
    "Figma Trigger (Beta)": {
      "main": [
        [
          {
            "node": "Posted by Max?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Posted by Max?": {
      "main": [
        [
          {
            "node": "Do nothing",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Posted by other user",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Posted by other user": {
      "main": [
        [
          {
            "node": "Wait 23 hours",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Wait 23 hours": {
      "main": [
        [
          {
            "node": "Fetch Figma file's comments",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Fetch Figma file's comments": {
      "main": [
        [
          {
            "node": "Split out comments",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Split out comments": {
      "main": [
        [
          {
            "node": "Filter out other comments",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Filter out other comments": {
      "main": [
        [
          {
            "node": "Comment not resolved?",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Comment not resolved?": {
      "main": [
        [
          {
            "node": "Replace me (Send message somewhere)",
            "type": "main",
            "index": 0
          }
        ],
        [
          {
            "node": "Comment resolved after 23hrs",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  }
}

type or paste code here

Looks like a credential issue - you need to add a Header Auth credential to use in the HTTP Request nodes. Below is a screenshot of what a Figma cred should look like (the key itself was changed so ofc you’ll have to furnish your own).

Let me know if that helps!

Thanks!
I didn’t know you had to authenticate 2x.