Fixing an issue with webhooks, couldn't use them in development (like getting schema) and making sure trigger will always use production app #3143.
This commit is contained in:
parent
ea6646f055
commit
88a729913c
|
@ -3,6 +3,7 @@ const { generateWebhookID, getWebhookParams } = require("../../db/utils")
|
|||
const toJsonSchema = require("to-json-schema")
|
||||
const validate = require("jsonschema").validate
|
||||
const triggers = require("../../automations/triggers")
|
||||
const { getDeployedAppID } = require("@budibase/auth/db")
|
||||
|
||||
const AUTOMATION_DESCRIPTION = "Generated from Webhook Schema"
|
||||
|
||||
|
@ -76,24 +77,34 @@ exports.buildSchema = async ctx => {
|
|||
}
|
||||
|
||||
exports.trigger = async ctx => {
|
||||
const db = new CouchDB(ctx.params.instance)
|
||||
const webhook = await db.get(ctx.params.id)
|
||||
// validate against the schema
|
||||
if (webhook.bodySchema) {
|
||||
validate(ctx.request.body, webhook.bodySchema)
|
||||
}
|
||||
const target = await db.get(webhook.action.target)
|
||||
if (webhook.action.type === exports.WebhookType.AUTOMATION) {
|
||||
// trigger with both the pure request and then expand it
|
||||
// incase the user has produced a schema to bind to
|
||||
await triggers.externalTrigger(target, {
|
||||
body: ctx.request.body,
|
||||
...ctx.request.body,
|
||||
appId: ctx.params.instance,
|
||||
})
|
||||
}
|
||||
ctx.status = 200
|
||||
ctx.body = {
|
||||
message: "Webhook trigger fired successfully",
|
||||
const prodAppId = getDeployedAppID(ctx.params.instance)
|
||||
try {
|
||||
const db = new CouchDB(prodAppId)
|
||||
const webhook = await db.get(ctx.params.id)
|
||||
// validate against the schema
|
||||
if (webhook.bodySchema) {
|
||||
validate(ctx.request.body, webhook.bodySchema)
|
||||
}
|
||||
const target = await db.get(webhook.action.target)
|
||||
if (webhook.action.type === exports.WebhookType.AUTOMATION) {
|
||||
// trigger with both the pure request and then expand it
|
||||
// incase the user has produced a schema to bind to
|
||||
await triggers.externalTrigger(target, {
|
||||
body: ctx.request.body,
|
||||
...ctx.request.body,
|
||||
appId: prodAppId,
|
||||
})
|
||||
}
|
||||
ctx.status = 200
|
||||
ctx.body = {
|
||||
message: "Webhook trigger fired successfully",
|
||||
}
|
||||
} catch (err) {
|
||||
if (err.status === 404) {
|
||||
ctx.status = 200
|
||||
ctx.body = {
|
||||
message: "Application not deployed yet.",
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,6 +6,7 @@ const { queue } = require("./bullboard")
|
|||
const newid = require("../db/newid")
|
||||
const { updateEntityMetadata } = require("../utilities")
|
||||
const { MetadataTypes } = require("../constants")
|
||||
const { getDeployedAppID } = require("@budibase/auth/db")
|
||||
|
||||
const WH_STEP_ID = definitions.WEBHOOK.stepId
|
||||
const CRON_STEP_ID = definitions.CRON.stepId
|
||||
|
@ -150,9 +151,13 @@ exports.checkForWebhooks = async ({ appId, oldAuto, newAuto }) => {
|
|||
await webhooks.save(ctx)
|
||||
const id = ctx.body.webhook._id
|
||||
newTrigger.webhookId = id
|
||||
// the app ID has to be development for this endpoint
|
||||
// it can only be used when building the app
|
||||
// but the trigger endpoint will always be used in production
|
||||
const prodAppId = getDeployedAppID(appId)
|
||||
newTrigger.inputs = {
|
||||
schemaUrl: `api/webhooks/schema/${appId}/${id}`,
|
||||
triggerUrl: `api/webhooks/trigger/${appId}/${id}`,
|
||||
triggerUrl: `api/webhooks/trigger/${prodAppId}/${id}`,
|
||||
}
|
||||
}
|
||||
return newAuto
|
||||
|
|
|
@ -5,20 +5,17 @@ const {
|
|||
doesHaveBasePermission,
|
||||
} = require("@budibase/auth/permissions")
|
||||
const builderMiddleware = require("./builder")
|
||||
const { isWebhookEndpoint } = require("./utils")
|
||||
|
||||
function hasResource(ctx) {
|
||||
return ctx.resourceId != null
|
||||
}
|
||||
|
||||
const WEBHOOK_ENDPOINTS = new RegExp(
|
||||
["webhooks/trigger", "webhooks/schema"].join("|")
|
||||
)
|
||||
|
||||
module.exports =
|
||||
(permType, permLevel = null) =>
|
||||
async (ctx, next) => {
|
||||
// webhooks don't need authentication, each webhook unique
|
||||
if (WEBHOOK_ENDPOINTS.test(ctx.request.url)) {
|
||||
if (isWebhookEndpoint(ctx)) {
|
||||
return next()
|
||||
}
|
||||
|
||||
|
|
|
@ -9,6 +9,7 @@ const { isUserInAppTenant } = require("@budibase/auth/tenancy")
|
|||
const { getCachedSelf } = require("../utilities/global")
|
||||
const CouchDB = require("../db")
|
||||
const env = require("../environment")
|
||||
const { isWebhookEndpoint } = require("./utils")
|
||||
|
||||
module.exports = async (ctx, next) => {
|
||||
// try to get the appID from the request
|
||||
|
@ -38,6 +39,7 @@ module.exports = async (ctx, next) => {
|
|||
// deny access to application preview
|
||||
if (
|
||||
isDevAppID(requestAppId) &&
|
||||
!isWebhookEndpoint(ctx) &&
|
||||
(!ctx.user || !ctx.user.builder || !ctx.user.builder.global)
|
||||
) {
|
||||
clearCookie(ctx, Cookies.CurrentApp)
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
const WEBHOOK_ENDPOINTS = new RegExp(
|
||||
["webhooks/trigger", "webhooks/schema"].join("|")
|
||||
)
|
||||
|
||||
exports.isWebhookEndpoint = ctx => {
|
||||
return WEBHOOK_ENDPOINTS.test(ctx.request.url)
|
||||
}
|
Loading…
Reference in New Issue