Skip to content
This repository has been archived by the owner on Jul 15, 2021. It is now read-only.

Add documentation for making autowireable Guzzle client with custom class #236

Open
rvanlaak opened this issue Aug 22, 2018 · 7 comments
Open

Comments

@rvanlaak
Copy link
Contributor

Another use case to document; changing the client's class, and how to autowire that to another own service definition.

Possible content

The bundle can get used as "a factory" to create an autowireable class. That way the bundle puts the middleware (like logging / error reporting / timing) in place.

<?php

namespace Acme\Infra\Shopping;

class Client extends \GuzzleHttp\Client
{
}
csa_guzzle:
    clients:
        shopping:
            class: 'Acme\Infra\Shopping\Client'
            config:
                base_uri: '%shopping.base_uri%'

When someone wants to autowire that class in their own service definition:

services:
    Acme\Application\Shopping\Cart:
        arguments: ['@Acme\Infra\Shopping\Client']   

Important note:

For controller action argument autowiring this works perfectly, but for resolving service arguments on container compilation this would unfortunately give a "service not found" exception because the bundle would register the client to the container after it resolved the rest of the services.

A way the container can resolve / autowire is by aliasing the service this bundle creates:

services:
    Acme\Infra\Shopping\Client:
        alias: 'csa_guzzle.client.shopping'

Probably a solution that wouldn't need this additional service alias, is by somewhere changing compilation priorities. Can bundles do their work several steps earlier in the compilation process?

@csarrazi
Copy link
Owner

Thanks for the suggestion! I definitely agree, we should provide documentation for such use case.

In any case, if you wish to provide a doc PR, feel free to fork the project, and change the files in the src/Resources/doc folder :)

One thing though: is there any specific reason for extending the client, instead of wrapping it in a decorator class?

@micayael
Copy link

micayael commented Apr 5, 2019

Hi @csarrazi. Is there some documentation about this?

@csarrazi
Copy link
Owner

csarrazi commented Apr 8, 2019

Hy @micayael not yet. I'm still waiting for someone to make a PR for this, as I am a bit short on time, these days.

@micayael
Copy link

micayael commented Apr 8, 2019

Thanks for reply @csarrazi.

Do you know if this is posible? I am trying multiple things but without success. if you could give me a little light on this I could help with the documentation

@csarrazi
Copy link
Owner

The main reason for that I wish to encourage composition instead of inheritance.
Meaning that instead of extending the Guzzle client, it would be better to wrap the client in a class exposing only business logic.

@micayael
Copy link

@csarrazi I think I've accomplished with your explanation

I configure the client with own configuration in csa_guzzle.yaml or config.yml

csa_guzzle:
    profiler: '%kernel.debug%'
    clients:
        client1:
            config:
                base_uri: http://localhost:8000
                timeout: 3.0
                headers:
                    "Content-Type": application/json

I create a Symfony service wrapping my client in services.yaml

services:

    App\MyOwnClient:
        arguments: ['@csa_guzzle.client.client1']

My Symfony service use the internal client in MyOwnClient.php

<?php

namespace App;

use GuzzleHttp\Client;

class RulerClient
{
    private $client;

    public function __construct(Client $client)
    {
        $this->client = $client;
    }
    
    public function ownMethod(string $path, array $data)
    {
        $response = $this->client->post($path, [
            'json' => $data
        ]);
        
        return $response;
    }
}

Now I can use it and I have the symfony profile functional

@csarrazi
Copy link
Owner

👍

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

No branches or pull requests

3 participants