openapi-psr7-validator icon indicating copy to clipboard operation
openapi-psr7-validator copied to clipboard

Validation of callbacks

Open digilist opened this issue 6 years ago • 6 comments
trafficstars

Some way to validate the request and response of callbacks would be great.

I think the validation per se would work, but there needs to be some other way to resolve the specs. Right now, the specs are loaded based on a passed OperationAddress which doesn't fit for callbacks.

digilist avatar Aug 12 '19 15:08 digilist

Sounds interesting. Can you provide an example of how it should look/work?

lezhnev74 avatar Aug 12 '19 15:08 lezhnev74

In the OpenAPI spec the callbacks are defined for one particular endpoint. So it would be necessary to define which callback should be validated, as I think there is no direct way to resolve it automatically.

It's possible to get a callback operation object like this:

$validatorBuilder = (new ValidatorBuilder)->fromJson('...');
$schema = $validatorBuilder->getServerRequestValidator()->getSchema();

$callbacks = $schema->paths['/foobar']->post->callbacks; // Depends on path and method where callback is defined

/** @var Callback $callback */
$callback = $callbacks['entity_created']; // Callback name

/** @var Operation $callbackOperation */
$callbackOperation = $callback->getRequest()->post; // Method of callback request

(I think it would be nice to make it a little easier to resolve this)

After we got the callback operation, we can use it to validate a PSR7 request object. The actual validation can be the same as it is at the moment, we just need to adjust how the operation is resolved (based on OperationAddress and SpecFinder (via the path) won't work here).

A very simple solution would be to implement a Subclass CallbackAddress from OperationAddress that contains the additional properties that are necessary to resolve the callback. Furthermore, the SpecFinder would need to consider this subclass and return the callback operation. (I think it can be a little bit cleaner with some new interfaces, but didn't think this through yet.)

This would allow to use any validator for a callback request. In addition it would be great to have some CallbackValidator that automates some stuff, so that it's e.g. not necessary to instantiate the validators manually.

digilist avatar Aug 12 '19 15:08 digilist

Adding more docs:

  • https://swagger.io/docs/specification/callbacks/
  • https://github.com/OAI/OpenAPI-Specification/blob/master/versions/3.0.2.md#callback-object

lezhnev74 avatar Aug 13 '19 07:08 lezhnev74

IMO callback operation is a just (OperationAddress + callback name) object. OperationAddress is known either implicitly with ServerRequestValidator (as a result of validation) or explicitly with RoutetServerRequestValidator (as an external argument) and callback name is the thing operated by userland code (i.e one could write a iterator thru all callbacks of current route and at this moment we have opaddr and callback name)

@digilist what will be validated against callback schema? could you provide sample use case (at least some pseudo code).

@lezhnev74 I hope we can do another PSR wrapper, for example PSR-18 decorator

scaytrase avatar Aug 13 '19 08:08 scaytrase

The use case I am facing is that I need to ensure that the callback is triggered only with a valid payload and that the callback response is only processed if it is in the correct format.

As we are dealing with quite complex payloads, it should be another internal measurement to ensure we do not make any mistakes.

digilist avatar Aug 13 '19 08:08 digilist

Speaking of PSR-18, the package lacks support for Request class. I think it is a good first step to add support for it.

lezhnev74 avatar Aug 13 '19 14:08 lezhnev74