Skip to content

Commit 2bb0018

Browse files
authored
Service locator for method resolver (#37)
1 parent feba1d5 commit 2bb0018

File tree

8 files changed

+142
-41
lines changed

8 files changed

+142
-41
lines changed

features/demo_app/default_config/services.yaml

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -18,16 +18,8 @@ services:
1818
tags:
1919
- { name: 'json_rpc_http_server.jsonrpc_method', method: 'bundledGetAnotherDummy' }
2020

21-
## Resolver mock
22-
resolver:
23-
class: DemoApp\Resolver\JsonRpcMethodResolver
24-
tags: ['json_rpc_http_server.method_aware']
25-
2621
## Mapping aware service
2722
mapping_aware_service:
2823
public: true # In order to allow Behat context to load it later
2924
class: DemoApp\Collector\MappingCollector
3025
tags: ['json_rpc_http_server.method_aware']
31-
32-
# Alias resolver mock to bundle resolver
33-
json_rpc_http_server.alias.method_resolver: '@resolver'

features/demo_app/src/Resolver/JsonRpcMethodResolver.php

Lines changed: 0 additions & 33 deletions
This file was deleted.

src/DependencyInjection/JsonRpcHttpServerExtension.php

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@ public function load(array $configs, ContainerBuilder $container)
5555
);
5656
$loader->load('sdk.services.app.yaml');
5757
$loader->load('sdk.services.infra.yaml');
58+
$loader->load('services.private.yaml');
5859
$loader->load('services.public.yaml');
5960
}
6061

@@ -159,11 +160,18 @@ private function binJsonRpcMethods(ContainerBuilder $container) : void
159160
$jsonRpcMethodDefinitionList = (new JsonRpcMethodDefinitionHelper())
160161
->findAndValidateJsonRpcMethodDefinition($container);
161162

163+
$methodMappingList = [];
162164
foreach ($jsonRpcMethodDefinitionList as $jsonRpcMethodServiceId => $methodNameList) {
163165
foreach ($methodNameList as $methodName) {
166+
$methodMappingList[$methodName] = new Reference($jsonRpcMethodServiceId);
164167
$this->bindJsonRpcMethod($methodName, $jsonRpcMethodServiceId, $mappingAwareServiceDefinitionList);
165168
}
166169
}
170+
171+
// Service locator for method resolver
172+
// => first argument is an array of wanted service with keys as alias for internal use
173+
$container->getDefinition('json_rpc_http_server.service_locator.method_resolver')
174+
->setArgument(0, $methodMappingList);
167175
}
168176

169177
/**

src/Resolver/MethodResolver.php

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
<?php
2+
namespace Yoanm\SymfonyJsonRpcHttpServer\Resolver;
3+
4+
use Psr\Container\ContainerInterface;
5+
use Yoanm\JsonRpcServer\Domain\JsonRpcMethodInterface;
6+
use Yoanm\JsonRpcServer\Domain\JsonRpcMethodResolverInterface;
7+
8+
/**
9+
* Class MethodResolver
10+
*/
11+
class MethodResolver implements JsonRpcMethodResolverInterface
12+
{
13+
/** @var ContainerInterface */
14+
private $locator;
15+
16+
public function __construct(ContainerInterface $locator)
17+
{
18+
$this->locator = $locator;
19+
}
20+
21+
/**
22+
* {@inheritdoc}
23+
*/
24+
public function resolve(string $methodName) : ?JsonRpcMethodInterface
25+
{
26+
return $this->locator->has($methodName)
27+
? $this->locator->get($methodName)
28+
: null
29+
;
30+
}
31+
}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
services:
2+
_defaults:
3+
public: false
4+
5+
json_rpc_http_server.service_locator.method_resolver:
6+
class: Symfony\Component\DependencyInjection\ServiceLocator
7+
tags: ['container.service_locator']
8+
arguments:
9+
- [] # <-- Will be defined during container compilation
10+
11+
# Alias method resolver (used in sdk.services.app.yml)
12+
json_rpc_http_server.alias.method_resolver: '@json_rpc_http_server.method_resolver'
13+

src/Resources/config/services.public.yaml

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,7 @@ services:
1212
arguments:
1313
- '@event_dispatcher'
1414

15+
json_rpc_http_server.method_resolver:
16+
class: Yoanm\SymfonyJsonRpcHttpServer\Resolver\MethodResolver
17+
arguments:
18+
- '@json_rpc_http_server.service_locator.method_resolver'

tests/Functional/DependencyInjection/ConfigFilesTest.php

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
<?php
22
namespace Tests\Functional\DependencyInjection;
33

4+
use Symfony\Component\DependencyInjection\ServiceLocator;
45
use Tests\Common\DependencyInjection\AbstractTestClass;
56
use Yoanm\JsonRpcServer\App\Creator\ResponseCreator;
67
use Yoanm\JsonRpcServer\App\Handler\ExceptionHandler;
@@ -14,6 +15,7 @@
1415
use Yoanm\SymfonyJsonRpcHttpServer\DependencyInjection\JsonRpcHttpServerExtension;
1516
use Yoanm\SymfonyJsonRpcHttpServer\Dispatcher\SymfonyJsonRpcServerDispatcher;
1617
use Yoanm\SymfonyJsonRpcHttpServer\Endpoint\JsonRpcHttpEndpoint;
18+
use Yoanm\SymfonyJsonRpcHttpServer\Resolver\MethodResolver;
1719

1820
/**
1921
* /!\ This test class does not cover JsonRpcHttpServerExtension, it covers yaml configuration files
@@ -132,4 +134,23 @@ public function provideBundlePublicServiceIdAndClass()
132134
],
133135
];
134136
}
137+
138+
/**
139+
* @return array
140+
*/
141+
public function provideBundlePrivateServiceIdAndClass()
142+
{
143+
return [
144+
'Bundle - Private - JSON-RPC method resolver ServiceLocator' => [
145+
'serviceId' => 'json_rpc_http_server.service_locator.method_resolver',
146+
'serviceClassName' => ServiceLocator::class,
147+
'public' => true,
148+
],
149+
'Bundle - Private - MethodResolver alias' => [
150+
'serviceId' => 'json_rpc_http_server.alias.method_resolver',
151+
'serviceClassName' => MethodResolver::class,
152+
'public' => true,
153+
],
154+
];
155+
}
135156
}
Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,65 @@
1+
<?php
2+
namespace Tests\Functional\Endpoint;
3+
4+
use PHPUnit\Framework\TestCase;
5+
use Prophecy\Prophecy\ObjectProphecy;
6+
use Psr\Container\ContainerInterface;
7+
use Yoanm\JsonRpcServer\Domain\JsonRpcMethodInterface;
8+
use Yoanm\SymfonyJsonRpcHttpServer\Resolver\MethodResolver;
9+
10+
/**
11+
* @covers Yoanm\SymfonyJsonRpcHttpServer\Resolver\MethodResolver
12+
*/
13+
class MethodResolverTest extends TestCase
14+
{
15+
/** @var MethodResolver */
16+
private $resolver;
17+
18+
/** @var ContainerInterface|ObjectProphecy */
19+
private $locator;
20+
21+
protected function setUp()
22+
{
23+
$this->locator = $this->prophesize(ContainerInterface::class);
24+
25+
$this->resolver = new MethodResolver(
26+
$this->locator->reveal()
27+
);
28+
}
29+
30+
public function testShouldReturnJsonRpcMethodIfRegistered()
31+
{
32+
$methodName = 'method_name';
33+
34+
$method = $this->prophesize(JsonRpcMethodInterface::class);
35+
36+
$this->locator->has($methodName)
37+
->willReturn(true)
38+
->shouldBeCalled()
39+
;
40+
41+
$this->locator->get($methodName)
42+
->willReturn($method->reveal())
43+
->shouldBeCalled()
44+
;
45+
46+
$this->assertSame(
47+
$method->reveal(),
48+
$this->resolver->resolve($methodName)
49+
);
50+
}
51+
52+
public function testShouldReturnNullIfNoMethodRegisteredForGivenName()
53+
{
54+
$methodName = 'method_name';
55+
56+
$this->locator->has($methodName)
57+
->willReturn(false)
58+
->shouldBeCalled()
59+
;
60+
61+
$this->assertNull(
62+
$this->resolver->resolve($methodName)
63+
);
64+
}
65+
}

0 commit comments

Comments
 (0)