Skip to main content

benecaster_register_integration_action()

Free
benecaster_register_integration_action( string $addon_slug, string $action, array $args ): bool

Declares one action an outside system — Zapier, Make, a CRM — may call through POST /wp-json/benecaster/v1/actions to make your add-on do something. Benecaster owns the endpoint, the sign-in, the checks, the idempotency and the call log; your add-on owns only the handler. Call it from the bootstrap you pass to benecaster_register_addon().

The caller signs in with a WordPress Application Password for a user with the Benecaster Integration role, and names the action, the show, an optional idempotency key and the data. Before your handler runs, Benecaster checks the caller may run integration actions, that the action is registered, that your add-on is active on the show, and that every declared field is present and of the right type. A repeat of the same request with the same idempotency key within 24 hours returns the first answer and never calls your handler twice.

$data holds only your declared fields, already coerced. Zapier and Make send most values as strings, so the check is lenient: an integer field accepts "12" and your handler receives 12; a boolean accepts true/false/1/0 in any form. A key you did not declare is dropped, not refused. Field types: string, integer, number, boolean, array, object.

Parameters

Name Type Default Required Description
addon_slug string — Yes The slug your add-on registered with in benecaster_register_addon(); either form works.
action string — Yes The action name, {addon-slug}.{noun}.{verb} — the same rule as webhook events: your catalog slug, then lowercase letters, digits and _ in the noun and verb, at most 191 characters. Example: podcast-workflow.guest.crm_linked.
args array — Yes handler (required callable, function ( array $data, int $show_id, int $user_id ): array|\WP_Error), fields (field name → [ 'type' => …, 'required' => bool, 'description' => string ]; default []) and label (string, translated by your add-on; default '').

Return Value

Type: bool

true when the action is registered — registering the same name again from the same add-on replaces it — and false when it is refused. Every refusal is also reported with _doing_it_wrong().

Example

add_action( 'benecaster_boot', function ( \Benecaster\Container $container ) {
    benecaster_register_addon( 'my-addon', static function (): void {
        benecaster_register_integration_action( 'my-addon', 'my-addon.booking.paid', [
            'label'   => __( 'A booking was paid elsewhere', 'my-addon' ),
            'fields'  => [
                'booking_id' => [ 'type' => 'integer', 'required' => true ],
                'invoice_id' => [ 'type' => 'string', 'required' => true ],
            ],
            'handler' => static function ( array $data, int $show_id, int $user_id ): array|\WP_Error {
                update_post_meta( $data['booking_id'], '_invoice_id', $data['invoice_id'] );
                return [ 'booking_id' => $data['booking_id'], 'status' => 'paid' ];
            },
        ] );
    } );
} );

Hooks Fired

Notes

Refused when your add-on has not called benecaster_register_addon(); the name is not under your add-on's own prefix; the name is malformed; your slug is one of Benecaster's own webhook families; handler is missing or not callable; or a field has an unknown type or a malformed name.

Return ids, not personal data. The first response is stored for 24 hours to answer a repeated idempotency key. Return a WP_Error with [ 'status' => 4xx ] to refuse (default 422); that refusal is remembered and replayed. Throw, or return a 5xx, only for a failure worth retrying — the key is then released so the retry runs.

Check that the record belongs to $show_id. Benecaster checked your add-on is active on the show the caller named, not that the caller's record ID is one of that show's records. Worked example: the recipe Let Zapier, Make or a CRM call your add-on.

Need this built rather than just documented? See our services →