19
19
use ApiPlatform \Core \Api \OperationType ;
20
20
use ApiPlatform \Core \Api \UrlGeneratorInterface ;
21
21
use ApiPlatform \Core \DataProvider \ItemDataProviderInterface ;
22
+ use ApiPlatform \Core \DataProvider \OperationDataProviderTrait ;
23
+ use ApiPlatform \Core \DataProvider \SubresourceDataProviderInterface ;
22
24
use ApiPlatform \Core \Exception \InvalidArgumentException ;
25
+ use ApiPlatform \Core \Exception \InvalidIdentifierException ;
23
26
use ApiPlatform \Core \Exception \ItemNotFoundException ;
24
27
use ApiPlatform \Core \Exception \RuntimeException ;
25
28
use ApiPlatform \Core \Identifier \Normalizer \ChainIdentifierDenormalizer ;
26
29
use ApiPlatform \Core \Metadata \Property \Factory \PropertyMetadataFactoryInterface ;
27
30
use ApiPlatform \Core \Metadata \Property \Factory \PropertyNameCollectionFactoryInterface ;
31
+ use ApiPlatform \Core \Util \AttributesExtractor ;
28
32
use ApiPlatform \Core \Util \ClassInfoTrait ;
29
33
use Symfony \Component \PropertyAccess \PropertyAccess ;
30
34
use Symfony \Component \PropertyAccess \PropertyAccessorInterface ;
39
43
final class IriConverter implements IriConverterInterface
40
44
{
41
45
use ClassInfoTrait;
46
+ use OperationDataProviderTrait;
42
47
43
- private $ itemDataProvider ;
44
48
private $ routeNameResolver ;
45
49
private $ router ;
46
50
private $ identifiersExtractor ;
47
- private $ identifierDenormalizer ;
48
51
49
- public function __construct (PropertyNameCollectionFactoryInterface $ propertyNameCollectionFactory , PropertyMetadataFactoryInterface $ propertyMetadataFactory , ItemDataProviderInterface $ itemDataProvider , RouteNameResolverInterface $ routeNameResolver , RouterInterface $ router , PropertyAccessorInterface $ propertyAccessor = null , IdentifiersExtractorInterface $ identifiersExtractor = null , ChainIdentifierDenormalizer $ identifierDenormalizer = null )
52
+ public function __construct (PropertyNameCollectionFactoryInterface $ propertyNameCollectionFactory , PropertyMetadataFactoryInterface $ propertyMetadataFactory , ItemDataProviderInterface $ itemDataProvider , RouteNameResolverInterface $ routeNameResolver , RouterInterface $ router , PropertyAccessorInterface $ propertyAccessor = null , IdentifiersExtractorInterface $ identifiersExtractor = null , ChainIdentifierDenormalizer $ identifierDenormalizer = null , SubresourceDataProviderInterface $ subresourceDataProvider = null )
50
53
{
51
54
$ this ->itemDataProvider = $ itemDataProvider ;
52
55
$ this ->routeNameResolver = $ routeNameResolver ;
53
56
$ this ->router = $ router ;
57
+ $ this ->identifiersExtractor = $ identifiersExtractor ;
54
58
$ this ->identifierDenormalizer = $ identifierDenormalizer ;
59
+ $ this ->subresourceDataProvider = $ subresourceDataProvider ;
55
60
56
61
if (null === $ identifiersExtractor ) {
57
- @trigger_error ('Not injecting ItemIdentifiersExtractor is deprecated since API Platform 2.1 and will not be possible anymore in API Platform 3 ' , E_USER_DEPRECATED );
62
+ @trigger_error (sprintf ( 'Not injecting "%s" is deprecated since API Platform 2.1 and will not be possible anymore in API Platform 3 ' , IdentifiersExtractorInterface::class) , E_USER_DEPRECATED );
58
63
$ this ->identifiersExtractor = new IdentifiersExtractor ($ propertyNameCollectionFactory , $ propertyMetadataFactory , $ propertyAccessor ?? PropertyAccess::createPropertyAccessor ());
59
- } else {
60
- $ this ->identifiersExtractor = $ identifiersExtractor ;
61
- }
62
-
63
- if (null === $ identifierDenormalizer ) {
64
- @trigger_error (sprintf ('Not injecting "%s" is deprecated since API Platform 2.2 and will not be possible anymore in API Platform 3. ' , ChainIdentifierDenormalizer::class), E_USER_DEPRECATED );
65
64
}
66
65
}
67
66
@@ -76,18 +75,31 @@ public function getItemFromIri(string $iri, array $context = [])
76
75
throw new InvalidArgumentException (sprintf ('No route matches "%s". ' , $ iri ), $ e ->getCode (), $ e );
77
76
}
78
77
79
- if (!isset ($ parameters ['_api_resource_class ' ], $ parameters [ ' id ' ] )) {
78
+ if (!isset ($ parameters ['_api_resource_class ' ])) {
80
79
throw new InvalidArgumentException (sprintf ('No resource associated to "%s". ' , $ iri ));
81
80
}
82
81
83
- $ identifiers = $ parameters ['id ' ];
82
+ $ attributes = AttributesExtractor::extractAttributes ($ parameters );
83
+
84
+ try {
85
+ $ identifiers = $ this ->extractIdentifiers ($ parameters , $ attributes );
86
+ } catch (InvalidIdentifierException $ e ) {
87
+ throw new InvalidArgumentException ($ e ->getMessage (), $ e ->getCode (), $ e );
88
+ }
84
89
85
90
if ($ this ->identifierDenormalizer ) {
86
- $ identifiers = $ this ->identifierDenormalizer ->denormalize ((string ) $ parameters ['id ' ], $ parameters ['_api_resource_class ' ]);
87
91
$ context [ChainIdentifierDenormalizer::HAS_IDENTIFIER_DENORMALIZER ] = true ;
88
92
}
89
93
90
- if ($ item = $ this ->itemDataProvider ->getItem ($ parameters ['_api_resource_class ' ], $ identifiers , $ parameters ['_api_item_operation_name ' ] ?? null , $ context )) {
94
+ if (isset ($ attributes ['subresource_operation_name ' ])) {
95
+ if ($ item = $ this ->getSubresourceData ($ identifiers , $ attributes , $ context )) {
96
+ return $ item ;
97
+ }
98
+
99
+ throw new ItemNotFoundException (sprintf ('Item not found for "%s". ' , $ iri ));
100
+ }
101
+
102
+ if ($ item = $ this ->getItemData ($ identifiers , $ attributes , $ context )) {
91
103
return $ item ;
92
104
}
93
105
0 commit comments