Webhooks: support for JWT / Wix

My client has a Wix website and I need to send creates and updates to Retool.

Wix allows calling webhooks, but when I test sending data to Retool I get a 400. This is probably because Wix sends the data as a JWT.

So now I have to set up an AWS lambda just to undress and validate the JWT

Would be nice if Retool webhooks just allowed this kind of data to be received. I'm not asking for any kind of deep JWT support (with decoding and validation), rather just for the possibility to do it myself.


Hello @Toon_Alfrink!

Can you provide a sample request in a screenshot so I can help to better troubleshoot what might be causing this 400 error?

Just to confirm, you want your Wix website to hit Retool, to trigger a retool workflow?

Trigger a workflow.

Unfortunately I can't give a sample request because Wix sends it from their back-end. I recommend you make a Wix account yourself so you can faithfully and repeatedly reproduce this. Anyway, when I routed it to an AWS Lambda I got this:

2024-04-16T14:13:29.702Z dd02c1cf-5774-487f-981c-88bac312c255 INFO {
version: '2.0',
routeKey: '$default',
rawPath: '/',
rawQueryString: '',
headers: {
'x-amzn-tls-cipher-suite': 'ECDHE-RSA-AES128-GCM-SHA256',
'content-length': '4042',
'x-amzn-tls-version': 'TLSv1.2',
'x-amzn-trace-id': 'Root=1-661e8789-76be2e4418f107fb6bf30d68',
'x-forwarded-proto': 'https',
host: 'p7zkj6vikymsu4gonpgrdmin5i0iwmsl.lambda-url.eu-central-1.on.aws',
'x-forwarded-port': '443',
'content-type': 'text/plain; charset=UTF-8',
'x-forwarded-for': '',
'user-agent': 'AHC/2.1',
accept: '/'
requestContext: {
accountId: 'anonymous',
apiId: 'p7zkj6vikymsu4gonpgrdmin5i0iwmsl',
domainName: 'p7zkj6vikymsu4gonpgrdmin5i0iwmsl.lambda-url.eu-central-1.on.aws',
domainPrefix: 'p7zkj6vikymsu4gonpgrdmin5i0iwmsl',
http: {
method: 'POST',
path: '/',
protocol: 'HTTP/1.1',
sourceIp: '',
userAgent: 'AHC/2.1'
requestId: 'dd02c1cf-5774-487f-981c-88bac312c255',
routeKey: '$default',
stage: '$default',
time: '16/Apr/2024:14:13:29 +0000',
timeEpoch: 1713276809696
body: 'eyJraWQiOiJJNnpKTkRLaSIsImFsZyI6IlJTMjU2In0.eyJkYXRhIjoie1wiZGF0YVwiOlwie1xcXCJvcmRlclxcXCI6IHtcXFwiaWRcXFwiOiBcXFwiZmVkYjE5ZjUtYmQ0Yy00YmZjLWIyZDEtMjEyNTM4MzE5NjExXFxcIixcXFwibnVtYmVyXFxcIjogMTAwOTYsXFxcImRhdGVDcmVhdGVkXFxcIjogXFxcIjIwMjAtMDMtMThUMTY6NDc6NTkuMjIyWlxcXCIsXFxcImN1cnJlbmN5XFxcIjogXFxcIlVTRFxcXCIsXFxcIndlaWdodFVuaXRcXFwiOiBcXFwiTEJcXFwiLFxcXCJ0b3RhbHNcXFwiOiB7XFxcInN1YnRvdGFsXFxcIjogXFxcIjEwXFxcIixcXFwic2hpcHBpbmdcXFwiOiBcXFwiM1xcXCIsXFxcInRheFxcXCI6IFxcXCIzXFxcIixcXFwiZGlzY291bnRcXFwiOiBcXFwiMVxcXCIsXFxcInRvdGFsXFxcIjogXFxcIjE1XFxcIixcXFwid2VpZ2h0XFxcIjogXFxcIjMwXFxcIixcXFwicXVhbnRpdHlcXFwiOiAyfSxcXFwiYmlsbGluZ0luZm9cXFwiOiB7XFxcInBheW1lbnRNZXRob2RcXFwiOiBcXFwiUGF5UGFsXFxcIixcXFwiZXh0ZXJuYWxUcmFuc2FjdGlvbklkXFxcIjogXFxcInR4XzE4MDZcXFwiLFxcXCJwYXltZW50UHJvdmlkZXJUcmFuc2FjdGlvbklkXFxcIjogXFxcInR4XzE4MDZcXFwiLFxcXCJhZGRyZXNzXFxcIjoge1xcXCJmdWxsTmFtZVxcXCI6IHtcXFwiZmlyc3ROYW1lXFxcIjogXFxcIkpvaG5cXFwiLFxcXCJsYXN0TmFtZVxcXCI6IFxcXCJTbWl0aFxcXCJ9LFxcXCJjb3VudHJ5XFxcIjogXFxcIlVTXFxcIixcXFwiY2l0eVxcXCI6IFxcXCJOZXcgWW9ya1xcXCIsXFxcInppcENvZGVcXFwiOiBcXFwiOTI1NDRcXFwiLFxcXCJwaG9uZVxcXCI6IFxcXCIrOTcyIDU1NTIzNDU1NVxcXCIsXFxcImVtYWlsXFxcIjogXFxcIkl2YW51c2hrYUBleGFtcGxlLmNvbVxcXCJ9LFxcXCJwYWlkRGF0ZVxcXCI6IFxcXCIyMDIwLTAzLTE4VDE2OjQ3OjU5LjI0NFpcXFwifSxcXFwic2hpcHBpbmdJbmZvXFxcIjoge1xcXCJkZWxpdmVyeU9wdGlvblxcXCI6IFxcXCJFeHByZXNzXFxcIixcXFwiZXN0aW1hdGVkRGVsaXZlcnlUaW1lXFxcIjogXFxcIlRvZGF5XFxcIixcXFwic2hpcHBpbmdSZWdpb25cXFwiOiBcXFwiRWFzdCBjb2FzdFxcXCIsXFxcInNoaXBtZW50RGV0YWlsc1xcXCI6IHtcXFwiYWRkcmVzc1xcXCI6IHtcXFwiZnVsbE5hbWVcXFwiOiB7XFxcImZpcnN0TmFtZVxcXCI6IFxcXCJKb2huXFxcIixcXFwibGFzdE5hbWVcXFwiOiBcXFwiU21pdGhcXFwifSxcXFwiY291bnRyeVxcXCI6IFxcXCJVU1xcXCIsXFxcImNpdHlcXFwiOiBcXFwiTmV3IFlvcmtcXFwiLFxcXCJ6aXBDb2RlXFxcIjogXFxcIjkyNTQ0XFxcIixcXFwicGhvbmVcXFwiOiBcXFwiKzk3MiA1NTUyMzQ1NTVcXFwiLFxcXCJlbWFpbFxcXCI6IFxcXCJJdmFudXNoa2FAZXhhbXBsZS5jb21cXFwifSxcXFwiZGlzY291bnRcXFwiOiBcXFwiMFxcXCIsXFxcInRheFxcXCI6IFxcXCIxXFxcIixcXFwicHJpY2VEYXRhXFxcIjoge1xcXCJ0YXhJbmNsdWRlZEluUHJpY2VcXFwiOiBmYWxzZSxcXFwicHJpY2VcXFwiOiBcXFwiM1xcXCJ9fX0sXFxcInJlYWRcXFwiOiBmYWxzZSxcXFwiYXJjaGl2ZWRcXFwiOiBmYWxzZSxcXFwicGF5bWVudFN0YXR1c1xcXCI6IFxcXCJQQUlEXFxcIixcXFwiZnVsZmlsbG1lbnRTdGF0dXNcXFwiOiBcXFwiTk9UX0ZVTEZJTExFRFxcXCIsXFxcImxpbmVJdGVtc1xcXCI6IFt7XFxcImluZGV4XFxcIjogMSxcXFwicXVhbnRpdHlcXFwiOiAyLFxcXCJuYW1lXFxcIjogXFxcIm15IHByb2R1Y3RcXFwiLFxcXCJwcm9kdWN0SWRcXFwiOiBcXFwiYTFmOWQzMzctZjgzMS00NTI5LTMxZTYtNjdkYjhmZDRlMWFhXFxcIixcXFwibGluZUl0ZW1UeXBlXFxcIjogXFxcIlBIWVNJQ0FMXFxcIixcXFwib3B0aW9uc1xcXCI6IFtdLFxcXCJjdXN0b21UZXh0RmllbGRzXFxcIjogW10sXFxcIndlaWdodFxcXCI6IFxcXCIxNVxcXCIsXFxcInNrdVxcXCI6IFxcXCIxMjM0NTY3OFxcXCIsXFxcImRpc2NvdW50XFxcIjogXFxcIjFcXFwiLFxcXCJ0YXhcXFwiOiBcXFwiMVxcXCIsXFxcInByaWNlRGF0YVxcXCI6IHtcXFwidGF4SW5jbHVkZWRJblByaWNlXFxcIjogZmFsc2UsXFxcInByaWNlXFxcIjogXFxcIjVcXFwiLFxcXCJ0b3RhbFByaWNlXFxcIjogXFxcIjEwXFxcIn19XSxcXFwiYWN0aXZpdGllc1xcXCI6IFt7XFxcInR5cGVcXFwiOiBcXFwiT1JERVJfUExBQ0VEXFxcIixcXFwidGltZXN0YW1wXFxcIjogXFxcIjIwMjAtMDMtMThUMTY6NDc6NTkuMjIyWlxcXCJ9LHtcXFwidHlwZVxcXCI6IFxcXCJPUkRFUl9QQUlEXFxcIixcXFwidGltZXN0YW1wXFxcIjogXFxcIjIwMjAtMDMtMThUMTY6NDc6NTkuMjQ0WlxcXCJ9XSxcXFwiZnVsZmlsbG1lbnRzXFxcIjogW10sXFxcImRpc2NvdW50XFxcIjoge1xcXCJ2YWx1ZVxcXCI6IFxcXCIxXFxcIn0sXFxcImJ1eWVyTGFuZ3VhZ2VcXFwiOiBcXFwiZW5cXFwiLFxcXCJjaGFubmVsSW5mb1xcXCI6IHtcXFwidHlwZVxcXCI6IFxcXCJXRUJcXFwifSxcXFwiZW50ZXJlZEJ5XFxcIjoge1xcXCJpZFxcXCI6IFxcXCJlODUyNzRjZi0wNDdhLTQ5ODktYmFmZi1kYWM1ZTBjMzk3MWRcXFwiLFxcXCJpZGVudGl0eVR5cGVcXFwiOiBcXFwiVVNFUlxcXCJ9LFxcXCJsYXN0VXBkYXRlZFxcXCI6IFxcXCIyMDIwLTAzLTE4VDE2OjQ3OjU5LjI0NFpcXFwifX1cIixcImluc3RhbmNlSWRcIjpcImRjY2ZjYmU5LTc1MzMtNGJjNi1hYjI1LTY3ZDZhMDEwYzdhY1wiLFwiZXZlbnRUeXBlXCI6XCJPcmRlclBhaWRcIn0iLCJpYXQiOjE3MTMyNzY4MDksImV4cCI6MTcxNjg3NjgwOX0.g7o9kcsjph6whjyzQ2w7qh0Y3eIv0LVJQfT3bXkLkUBvPlc80NP7uh_4EhI6w1Y-nQrBCrYpbLq5rgZxpklZtMpz7pvfkCaADmh-hSzNuwY2MiRBT-90MFdl0KwdAk3hcOgrA9p8D4IeMK_tiahK6ULkr36B8MkZDM36R45Ky9t62KXqnSJDB1kapIfCw65aFbIBM_jFFBqsLaX6XXR5a3GTGfIluXymhjZ8qXvoB-ktScghCVxEYb44IIgSX3dQmgF4gpeqseaWD8Olc0E1sDfZqOHVlOg6fWG99rYZTDgkbgTm_fULMvumOsSVcHlwrqkyRwiKHMy6Oxho2ZwlWQ',
isBase64Encoded: false

Hey @Toon_Alfrink thank you for the information.

It looks like there are some docs on how Retool workflows do support webhook triggers where the incoming JSON payload can be accessed to grab data and details inside the flow here.

Can you check in your retool app's debugger tool to see if there is a more specific error message when the webhook comes in?

Given that a JWT would be in the header of a request hitting the workflow's trigger endpoint it shouldn't be getting blocked, I am guessing the issue is stemming from elsewhere.

You should be able to grab the JWT out of the incoming payload's header, then have workflow steps to decode and validate the token. Maybe the Wix url sending in the webhook isn't authorized by the app to hit the trigger endpoint.

I will make a Wix account and try to replicate the bug.

@Toon_Alfrink Could you share some information/screenshots on how you have the webhook/request set up in Wix?

Also have you tried using a cURL in your terminal to hit the workflow endpoint to see if you can trigger it from a non-Wix source?

I am not familiar to Wix and I am having some trouble setting up a create/update request. Thank you!

Keep in mind that link that I included seems to include the ID of my specific app so you'll need to substitute that

@Toon_Alfrink I was able to set up a button in Wix to trigger a Velo API function call using the getJSON method to a Retool workflow trigger API and it worked fine for me.

Workflows are able to access JSON payloads to grab and unpack data stored in the headers and body of a JSON request object such as JWTs so that you can decode and validate the tokens.

Can you share a screenshot of the Wix code that is dispatching the request to the Retool Webhook? (feel free to hide/obfuscate the Webhook URL and other sensitive data)

Reading through the docs on Webhook triggers here it says that Webhook events sent to the workflow endpoint must use Content-Type: application/json

Which could be the cause of a 400 error as the webhook needs the content type for the data to pass through to then be accessable in the then triggered Workflow.

Sorry to keep you in the dark, Jack. Here's a video to clarify how I'm getting an error. I'm not even using Velo.

Mind you I don't currently see a 400, I think Wix changed the way they report the error in this UI, but regardless it's not working

Hey @Toon_Alfrink!

Thank you for posting the video, however it seems that it's not playable. I can see the first frame but clicking anywhere on it doesn't seem to do anything.

Maybe try a link so I can watch and get a better idea on how to troubleshoot this bug for you!

Yeah that link expired in 2 days

Here's another: https://youtu.be/KpWmlThj4iw

Hey @Toon_Alfrink Thanks for posting the video.

Inside of Retool workflows there should be a 'run history' button in the bottom left that might be able to give us some more info on why the request coming in the the Retool URL isn't hitting the webhook trigger.

Normally once the trigger is hit you can access the headers, any tokens in the headers and the body of the request to handle as you like.

I have a hunch the request from Wix is erroring out before it can get to Retool, but the 'run history' can confirm or deny this.

Was your AWS redirect able to trigger the workflow? I was able to trigger a workflow from Wix with the below code snippet,

const url = "https://api.retool.com/v1/workflows/bfe79......."
$w.onReady(function () {

$w('#button2').onClick((event) => {
	.then(json => {