Register an add-on CPT with the custom field system
Benecaster registers benecaster_episode with the field system automatically. Add-ons that introduce their own CPTs (e.g. Guest Manager’s benecaster_guest) must call benecaster_register_field_cpt() inside a benecaster_boot callback so the CPT appears in the Field Group editor’s “Attached CPT” dropdown. Also shows using useFieldValues and useSaveFieldValues hooks in a React editor panel for the new CPT.
When to Use This
-
Your add-on introduces a custom post type with its own editor screen
-
You want podcasters to be able to create Field Groups and attach them to that CPT via Benecaster → Fields
-
You want to render those field groups in your editor using the same tabbed field UI the episode editor uses
-
You want field values to be stored and retrieved through the standard
benecaster_get_field()/benecaster_get_fields()API
Benecaster auto-registers benecaster_episode. Everything else must be registered explicitly at add-on boot.
How It Works
There are two halves — a one-line PHP registration and a React panel in your editor.
PHP — register the CPT at add-on boot. Call benecaster_register_field_cpt() inside a benecaster_boot callback, passing your CPT slug and a human-readable label. The label is what podcasters see in the “Attached CPT” dropdown of the Field Group editor.
React — fetch and save values in your editor. useFieldValues( cpt, objectId ) and useSaveFieldValues(), both exported from @benecaster/hooks/useFieldValues, accept any registered CPT slug. Pass yours and the record ID and you get back the same FieldGroupWithValues[] shape the episode editor uses, which the same field UI renders for you — no additional components required. Hold edited values in local state, and on save map them into an array of { field_id, value } pairs for the mutation.
useSaveFieldValues() POSTs to /benecaster/v1/field-values/{cpt}/{id}. That endpoint is already registered for every CPT once boot-time registration has happened, so there is nothing further to wire up on the server side.
Notes
Registration happens at boot, not on every request. benecaster_register_field_cpt() writes to an in-memory registry inside FieldRegistry. It fires once per request. Calling it outside a benecaster_boot callback risks running before the container is ready — always use the hook.
The benecaster_field_groups filter works for your CPT automatically. After registration, the filter fires with your CPT slug whenever the field editor loads. Add-ons can inject synthetic groups for your CPT using the same pattern as for episodes — see Inject a Dynamically Generated Field Group.
benecaster_get_field() and benecaster_get_fields() work for your CPT without any extra configuration. The REST endpoint and public functions respect CPT context because every stored field value carries the CPT slug it belongs to — field values are scoped per CPT automatically.
The useEpisodeFieldValues hook is a thin wrapper. It calls useFieldValues( 'benecaster_episode', episodeId ) internally. Your add-on calls useFieldValues directly with its own slug — no hook duplication needed.
Related
-
FieldRegistry— class reference for the CPT registry -
Custom Fields — overview of the Field Groups system for podcasters
Code
<?php
// PHP — register the CPT at add-on boot
add_action( 'benecaster_boot', function ( \Benecaster\Container $container ) {
benecaster_register_field_cpt( 'benecaster_guest', __( 'Guest', 'benecaster-guest-manager' ) );
} );
// React — fetch and save field values in a guest editor panel
// (see recipe page for full TSX example using useFieldValues / useSaveFieldValues)
Hooks Used
Need this built rather than just documented? See our services →