1

I'm using Slim Framework with PHP-DI to autowire dependencies for me. But one dependency is just a regular array. If I put a regular array into my container configuration, then all arrays will be set to that one array. So my primary question would be:

How do I inject just one single variable, while letting the container auto-wire the rest? Is this possible? I've found myself writing a route like this:

$app->get('/userConfig', function (
    Request $request, 
    Response $response,
    Preferences $prefs,
    UserConfig $userconfig)
{
    $myArray = ['Thing1','thing2','thing3'];
    return $userconfig->configView($request, $response, $myArray, $prefs);
});

Whereas all my other routes are short like this, because they only have dependencies on unique classes:

$app->get('/testPage', ['\Test','myTestPage']);

I wrote all that extra stuff just to squeeze $myArray into the configView function, is there a way to combine regular dependency injection with autowiring? Does any framework or library do that?

I could have just written it like this if I didn't need that one array:

$app->get('/userConfig', ['\UserConfig','configView']);

Alternatively, I could reach into the container and get the array, but that would make the page-function dependent on the container, which is something which should be avoided.

ADJenks
  • 2,973
  • 27
  • 38
  • I have added values to the container. But I don't want to call on the container from inside the class, I want to inject them, Injecting the container and calling on it would defeat the purpose of DI, and the motto: "Tell, Don't Ask.". – ADJenks Nov 25 '16 at 20:49

2 Answers2

1

You can't solve that with autowiring only. You have to write a bit of configuration to inject your array into the classes you need to: http://php-di.org/doc/php-definitions.html

See also here to read how to set up a configuration file with Slim and PHP-DI: http://php-di.org/doc/frameworks/slim.html#configuring-php-di

Matthieu Napoli
  • 48,448
  • 45
  • 173
  • 261
  • I understand how to add values to the container. The problem is that I want to add 'values' to the container, not 'Classes', but the problem with that is that you cannot use type hinting with 'values' and you need type hinting to use autowiring. – ADJenks Nov 25 '16 at 01:27
  • @adjenks yes, as I said **you can't solve that with autowiring only**. You need to use configuration, PHP-DI can't automatically guess which "string" or "array" you want if you type-hint "string" or "array". – Matthieu Napoli Nov 27 '16 at 21:26
  • I figured it out. Using call() allowed me to do what I wanted. – ADJenks Nov 30 '16 at 22:53
0

I needed to use the call() function of the container. As you can see in the question there is also a "Preferences" parameter for configView, however I did not have to pass it, the container did that for me. I didn't understand how to pass it partial sets of parameters, this is how, as an array in the second parameter of call() like so:

$app->get('/userConfig', function (
        Request $request, 
        Response $response
    ){
        $myArray = ['Thing1','thing2','thing3'];
        return $this->call(['UserConfig', 'configView'],[$request,$response,$myArray]);
    });

The key part being [$request,$response,$myArray] and not requiring EVERY OTHER parameter. In my example there is only one, but my actual object had 5 more, I wanted to know how to avoid dealing with the other parameters, this was how...

ADJenks
  • 2,973
  • 27
  • 38