Buffer is PressQueue's first provider. The shared code owns rules, "never share" rules, credentials, queue state and retries. A provider adapter handles the requests to the outside service. A companion plugin can register another provider through the pressqueue_provider_adapters filter. The filter starts with an empty array: Buffer is built in and always comes first, and a provider key that is already registered, including buffer, is skipped.
PressQueue builds the provider registry the first time a request needs it and keeps it for the rest of that request. A provider registered after that point shows up on the next request. The label shown for a provider is derived from its provider key.
Register a descriptor
Return a PressQueue\Provider\ProviderDescriptor from the filter:
add_filter(
'pressqueue_provider_adapters',
static function ( array $providers ): array {
$providers[] = new ProviderDescriptor(
'example_provider',
array( 'api_key' ),
static fn(): DiscoveryProvider => new ExampleDiscoveryProvider(),
static fn(): DeliveryProvider => new ExampleDeliveryProvider()
);
return $providers;
}
);
The constructor takes:
provider_key: a lowercase ASCII identifier matching[a-z][a-z0-9_]{0,63}.authentication_modes: a non-empty list of supported authentication modes.discovery_factory: a nullable callable without arguments that returns aDiscoveryProvider.delivery_factory: a nullable callable without arguments that returns aDeliveryProvider.
At least one factory is required. An invalid descriptor, a duplicate key, or an attempt to replace the reserved buffer key is ignored for that provider. If a factory throws, only that provider becomes unavailable for the current request. PressQueue reports a redacted adapter-unavailable error and does not expose the thrown message.
Discovery and delivery
Discovery adapters may read account, organization and channel metadata. They must not create social posts on the provider's side.
Delivery adapters receive ProviderDeliveryRequest objects created by the shared planner and worker gates. They return one normalized ProviderDeliveryResult, classified as accepted, retryable_failure, rate_limited, permanent_failure or ambiguous. An ambiguous result is never retried automatically; PressQueue asks the site owner to check the provider.
Public fields on the provider DTOs are immutable readonly properties.
Connection service
PressQueue has no generic credential screen for extension providers. The companion plugin collects the credentials and provides its own admin screens. Use PressQueue\Provider\ProviderConnectionService to create and synchronize the local connection state:
create_disabled_connection( $provider_key, $label, $credential, $authentication_mode )fetch_account( $connection, $credential )verify_account( $connection, $credential )sync_channels( $connection, $credential, $account, $organization_id, $preserve_enabled )
New connections and synced channels stay disabled until an operator switches them on. Changing the selected organization sets the connection back to unverified and disables the channels that belong to it.
Conformance tests
Reusable PHPUnit support lives under tests/Support/ in the plugin repository. Companion providers can extend ProviderConformanceTestCase in their own test suites to check DTO construction, immutable adapter boundaries, discovery success and failure classification, and normalized delivery results.
Rules that hold for every provider
- New connections, channels and rules start switched off.
- "Never share" rules and policy errors stop delivery.
- Each delivery keeps the same identity across retries.
- An uncertain reply from the provider is never retried automatically.