Managing URL parameters

Default behaviour

By default, when an action is created, each parameter of the function should be passed in the URL. Here is a sample:

/**
 * My action with 2 compulsory parameters.
 *
 * @URL("/test")
 * @param string $var1
 * @param string $var2
 */
public function my_action($var1, $var2) { ... } 

In this action, both parameters are compulsory. If one of the parameters is not passed by the user, an error message is displayed ("HTTP 400 Bad request" return code). Hopefully, you can get optional parameters using parameters default values:

/**
 * My action with 1 compulsory parameter and one optional.
 *
 * @URL("/test")
 * @param string $var1
 * @param string $var2
 */
public function my_action($var1, $var2 = 42) { ... } 

In this sample, if the user does not pass the "var2" parameter in the URL, it will be equal to 42. The URL might be: http://[server-url]/[webapp-path]/test?var1=param1

Injecting PSR-7 Request object as a parameter

Splash 7+ has native support for PSR-7 RequestInterface and for ServerRequestInterface objects.

This means that Splash will automatically inject a ServerRequest object into your action if your action expects a RequestInterface or a ServerRequestInterface object:

use Psr\Http\Message\ServerRequestInterface;
...

/**
 * My action with the request object filled
 *
 * @URL("/test")
 * @param ServerRequestInterface $request
 */
public function my_action(ServerRequestInterface $request) {
    $param = $request->getQueryParams()['param'];
    ...
} 

Note: you should use the ServerRequest object instead of accessing directly $_FILES, $_SERVER, $_COOKIES, or HTTP headers.

Advanced behaviour

You are a power user? Splash has a number of extension points including one that let's you define how parameters are injected in the action.

You can add your own plugins to automatically fill some parameters of the request (we call those ParameterFetchers).

You could write a parameter fetcher to:

  • automatically plug your ORM to Splash (by injecting entities directly into the action)
  • or inject a session
  • or inject services (à la Angular)
  • or really... whatever you might imagine!

Writing a parameter fetcher

To write a parameter fetcher, you need to implement the ParameterFetcher interface:

/**
 * Classes implementing this interface can create parameter fetchers that will fill parameters of actions.
 */
interface ParameterFetcher
{
    /**
     * Returns whether this fetcher factory can handle the parameter passed in parameter for the url $url.
     *
     * @param ReflectionParameter $reflectionParameter
     * @param string              $url
     *
     * @return bool
     */
    public function canHandle(ReflectionParameter $reflectionParameter, string $url = null) : bool;

    /**
     * Returns some data needed by this fetcher to fetch data from the request.
     * This data MUST be serializable (and will be serialized). This function will be called only once
     * and data cached. You can perform expensive computation in this function.
     *
     * @param ReflectionParameter $reflectionParameter
     * @param string|null         $url
     *
     * @return mixed
     */
    public function getFetcherData(ReflectionParameter $reflectionParameter, string $url = null);

    /**
     * Returns the value to be injected in this parameter.
     *
     * @param mixed                $data    The data generated by "getFetcherData"
     * @param SplashRequestContext $context
     *
     * @return mixed
     */
    public function fetchValue($data, SplashRequestContext $context);
}

Notice how there are 3 methods:

  • canHandle is called by Splash on each parameter. The parameter fetcher must return true is it can handle this parameter, or false if it cannot.
  • If canHandle returns true, getFetcherData is called. This method can return any serializable data that will be used to analyze the parameter. This method is called only once per parameter. The result is put in cache. You can perform expensive computation in this function.
  • fetchValue is where the real work happens. For each request and each parameter, the fetchValue method is called. It must return the value that is injected into the parameter. The fetchValue method receives the serialized data that was computed by the getFetcherData method along the request, bundled in the SplashRequestContext $context object.

Found a typo? Something is wrong in this documentation? Just fork and edit it!