Skip to content

Instantly share code, notes, and snippets.

@marcosoliveeira1
Created August 28, 2024 21:03
Show Gist options
  • Save marcosoliveeira1/c6af7a103a166cdfa611ebdd8d4a770a to your computer and use it in GitHub Desktop.
Save marcosoliveeira1/c6af7a103a166cdfa611ebdd8d4a770a to your computer and use it in GitHub Desktop.
Find Zap by Webhook URL
## Run this code in browser console
## Based on https://gist.github.com/ikbelkirasan/601dd8a51f458bf09d5ce44a102b9fd0
const getNodes = zap => {
let nodes = [];
for (let nodeId in zap.nodes) {
const node = zap.nodes[nodeId];
nodes.push(node);
}
return nodes;
};
const getZapNodes = async zapId => {
const response = await fetch(
`https://zapier.com/api/v3/zaps/${zapId}/nodes`
);
const { objects: nodes } = await response.json();
return nodes ?? [];
};
const openZap = (zapId, nodeId) => {
const a = document.createElement("a");
a.target = "_blank";
a.href = `https://zapier.com/app/editor/${zapId}/nodes/${nodeId}`;
a.click();
};
const fetchAccounts = async () => {
const response = await fetch("https://zapier.com/api/v3/accounts");
const { objects: accounts } = await response.json();
return accounts;
};
const fetchZaps = async accountId => {
const response = await fetch(
`https://zapier.com/api/v3/zaps?account_id=${accountId}`
);
const zaps = await response.json();
return zaps;
};
const getAllZaps = async () => {
const accounts = await fetchAccounts();
const allZaps = [];
for (const accountIndex in accounts) {
const account = accounts[accountIndex];
const { objects: zaps } = await fetchZaps(account.id);
allZaps.push(...zaps);
}
return allZaps;
};
const getZapFromWebhookId = async (zap, webhookId) => {
try {
const response = await fetch(`https://zapier.com/api/gulliver/steptesting/v1/zaps/${zap.id}/subscriptions?account_id=${zap.accountId}`);
const { subscriptions } = await response.json();
const webhookZap = subscriptions.find(obj => {
return obj?.hook_url.includes(webhookId);
});
return webhookZap ? zap : null;
} catch (error) {
return null;
}
};
const findWebhooks = zap => {
const nodes = getNodes(zap);
const webhookNodes = nodes.filter(node => {
return node["selected_api"] === "WebHookAPI";
});
return webhookNodes.map(node => {
return {
...node,
zapId: zap.id,
accountId: zap.account_id
};
});
};
const getWebhooks = zaps => {
const webhookZaps = [];
for (let zapId in zaps) {
const zap = zaps[zapId];
webhookZaps.push(...findWebhooks(zap));
}
return webhookZaps;
};
const parseWebhookUrl = webhookUrl => {
const regex = /https\:\/\/hooks\.zapier\.com\/hooks\/catch\/(\w+)\/(\w+)\/?/;
const matches = regex.exec(webhookUrl);
const [, accountId, webhookId] = matches;
return {
accountId,
webhookId
};
};
const fetchWebhookZaps = async (webhookZaps, webhookId, concurrency = 20) => {
const getZapFromWebhookId = async (zap, webhookId) => {
try {
const response = await fetch(`https://zapier.com/api/gulliver/steptesting/v1/zaps/${zap.id}/subscriptions?account_id=${zap.accountId}`);
const { subscriptions } = await response.json();
const webhookZap = subscriptions.find(obj => obj?.hook_url.includes(webhookId));
return webhookZap ? zap : null;
} catch (error) {
return null;
}
};
const fetchBatch = async (batch) => {
const results = await Promise.all(batch.map(webhookZap => getZapFromWebhookId(webhookZap, webhookId)));
return results.filter(result => result !== null);
};
const batches = [];
for (let i = 0; i < webhookZaps.length; i += concurrency) {
const batch = webhookZaps.slice(i, i + concurrency);
batches.push(fetchBatch(batch));
}
const results = await Promise.all(batches);
return results.flat();
};
const findZapForWebhookUrl = async webhookUrl => {
const zaps = await getAllZaps();
console.log("πŸ”Ž Found", zaps.length, "zaps.");
const webhookZaps = getWebhooks(zaps);
console.log("πŸ”Ž Found", webhookZaps.length, "webhooks.");
const { webhookId } = parseWebhookUrl(webhookUrl);
const foundZaps = await fetchWebhookZaps(webhookZaps, webhookId);
if (foundZaps.length > 0) {
console.log("πŸ”Ž Found the zap:", foundZaps);
return foundZaps;
}
};
async function run(webhookUrl) {
console.log(
"βŒ› Looking for the zap that matches your webhook URL. Please wait..."
);
const zap = await findZapForWebhookUrl(webhookUrl);
if (!zap) {
console.error("❌ Could not find the zap");
return false;
}
console.log(`⚑ Found the zap:, https://zapier.com/app/editor/${zap[0].zapId}`);
}
// πŸ‘‡ Paste your webhook URL here.
run("https://hooks.zapier.com/hooks/catch/XXXXX/XXXXXX");
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment