Skip to content

[HttpClient] Add UriTemplateHttpClient #49302

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged

Conversation

fancyweb
Copy link
Contributor

@fancyweb fancyweb commented Feb 8, 2023

Q A
Branch? 6.3
Bug fix? no
New feature? yes
Deprecations? no
Tickets -
License MIT
Doc PR -

This PR adds UriTemplateHttpClient to ease using URI templates (see https://www.rfc-editor.org/rfc/rfc6570) with symfony/http-client.

The goal is not to reimplement the RFC 6570 but to provide a better DX. A vendor has to be installed to expand the urls and we do not impose which one.

The simple usage is:

(new UriTemplateHttpClient())
    ->request('GET', 'https//ccc.tld/{resource}{?page}', [
        'vars' => [
            'resource' => 'users',
            'page' => 3,
         ],
    ]);
    // the requested url is https//ccc.tld/users?page=3

In a full framework context, all HTTP clients are decorated by UriTemplateHttpClient. The support is transparent and enabled globally.
It's possible to configure a custom expander by redefining the http_client.uri_template_expander alias.

@fancyweb fancyweb force-pushed the http-client/uri-template-client branch from 202fd20 to 8f69ae0 Compare February 8, 2023 18:31
@ro0NL
Copy link
Contributor

ro0NL commented Feb 8, 2023

global variables / UriTemplateHttpClient feels kinda weird to me, compared to request(template($uri, $vars))

@OskarStark OskarStark changed the title [HttpClient] Add UriTemplateHttpClient [HttpClient] Add UriTemplateHttpClient Feb 8, 2023
@fancyweb fancyweb force-pushed the http-client/uri-template-client branch 4 times, most recently from d638788 to 3568519 Compare February 16, 2023 12:31
Copy link
Member

@nicolas-grekas nicolas-grekas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

much simpler :)

@fancyweb fancyweb force-pushed the http-client/uri-template-client branch 3 times, most recently from 786db29 to 17d6368 Compare February 23, 2023 11:28
@fancyweb fancyweb force-pushed the http-client/uri-template-client branch from 17d6368 to 82c4133 Compare February 23, 2023 11:31
Copy link
Member

@nicolas-grekas nicolas-grekas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM thanks, just some minor things.

@fancyweb fancyweb force-pushed the http-client/uri-template-client branch 5 times, most recently from bdda79f to 5e90fc9 Compare February 23, 2023 18:06
Copy link
Member

@nicolas-grekas nicolas-grekas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM thanks (decoration issue can be dealt with separately in #49513)

@nicolas-grekas
Copy link
Member

Thank you @fancyweb.

@nicolas-grekas nicolas-grekas force-pushed the http-client/uri-template-client branch from d62d9b9 to 803a54e Compare February 24, 2023 08:08
@nicolas-grekas nicolas-grekas merged commit 0d57a3f into symfony:6.3 Feb 24, 2023
@fancyweb fancyweb deleted the http-client/uri-template-client branch February 24, 2023 08:25
nicolas-grekas added a commit that referenced this pull request Feb 24, 2023
…ation strategy (fancyweb)

This PR was merged into the 6.3 branch.

Discussion
----------

[FrameworkBundle][HttpClient] Refactor http_client decoration strategy

| Q             | A
| ------------- | ---
| Branch?       | 6.3
| Bug fix?      | no
| New feature?  | no
| Deprecations? | no
| Tickets       | #49302 (comment)
| License       | MIT
| Doc PR        | -

Commits
-------

11e2164 [FrameworkBundle][HttpClient] Refactor http_client decoration strategy
symfony-splitter pushed a commit to symfony/framework-bundle that referenced this pull request Mar 6, 2023
…ation strategy (fancyweb)

This PR was merged into the 6.3 branch.

Discussion
----------

[FrameworkBundle][HttpClient] Refactor http_client decoration strategy

| Q             | A
| ------------- | ---
| Branch?       | 6.3
| Bug fix?      | no
| New feature?  | no
| Deprecations? | no
| Tickets       | symfony/symfony#49302 (comment)
| License       | MIT
| Doc PR        | -

Commits
-------

11e2164ee5 [FrameworkBundle][HttpClient] Refactor http_client decoration strategy
nicolas-grekas added a commit that referenced this pull request Mar 28, 2023
…s into single-method interfaces (nicolas-grekas)

This PR was merged into the 6.3 branch.

Discussion
----------

[DependencyInjection] Add support for casting callables into single-method interfaces

| Q             | A
| ------------- | ---
| Branch?       | 6.3
| Bug fix?      | no
| New feature?  | yes
| Deprecations? | no
| Tickets       | -
| License       | MIT
| Doc PR        | -

This PR makes it possible to cast closures to single-method interfaces.

It is best reviewed [ignoring whitespaces](https://github.com/symfony/symfony/pull/49632/files?w=1).

This works at the service definition level. Here is an example that creates heterogeneous URI-template expanders and exposes them under a common interface (using real classes inspired from #49302):

```php
interface UriExpanderInterface
{
    public function expand(string $url, array $vars): string;
}
```

And then, in some service configuration using the PHP-DSL:

```php
    ->set('uri_expander.guzzle', UriExpanderInterface::class)
        ->fromCallable([\GuzzleHttp\UriTemplate\UriTemplate::class, 'expand'])

    ->set('uri_template_expander.rize', UriExpanderInterface::class)
        ->fromCallable([inline_service(\Rize\UriTemplate::class), 'expand'])

    ->alias(UriExpanderInterface::class, 'uri_template_expander.rize' or 'uri_template_expander.guzzle')
```

Internally, this creates a proxy class that will behave like this one (which could be used in a test case):

```php
$expander = new class ($closure) implements UriExpanderInterface {
    public function __construct(private \Closure $closure)
    {
    }

    public function expand(string $url, array $vars): string
    {
        return $this->closure->__invoke($url, $vars);
    }
};
```

This also adds support for YAML and XML of course:

```yaml
services:
    uri_template_expander.rize:
        class: UriExpanderInterface
        from_callable: [ !service {class: Rize\UriTemplate}, expand ]
```

```xml
<services>
  <service id="uri_template_expander.rize" class="UriExpanderInterface">
    <from-callable method="expand">
      <service class="Rize\UriTemplate"/>
    </from-callable>
  </service>
</services>
```

This also works using attributes:

```php
class MyClass
{
    public function __construct(
        #[AutowireCallable([\GuzzleHttp\UriTemplate\UriTemplate::class, 'expand'])]
        UriExpanderInterface $expander,
    )
}
```

Commits
-------

9975de2 [DependencyInjection] Make it possible to cast callables into single-method interfaces
@fabpot fabpot mentioned this pull request May 1, 2023
symfony-splitter pushed a commit to symfony/framework-bundle that referenced this pull request Jul 28, 2023
…ation strategy (fancyweb)

This PR was merged into the 6.3 branch.

Discussion
----------

[FrameworkBundle][HttpClient] Refactor http_client decoration strategy

| Q             | A
| ------------- | ---
| Branch?       | 6.3
| Bug fix?      | no
| New feature?  | no
| Deprecations? | no
| Tickets       | symfony/symfony#49302 (comment)
| License       | MIT
| Doc PR        | -

Commits
-------

11e2164ee5 [FrameworkBundle][HttpClient] Refactor http_client decoration strategy
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants