29
29
*/
30
30
class Reference implements SpecObjectInterface, DocumentContextInterface
31
31
{
32
+ /** @var array<string, mixed> */
33
+ private static $ relativeReferencesCache = [];
34
+
32
35
/**
33
36
* @var string
34
37
*/
@@ -296,14 +299,18 @@ private function resolveTransitiveReference(Reference $referencedObject, Referen
296
299
*/
297
300
private function adjustRelativeReferences ($ referencedDocument , $ basePath , $ baseDocument = null , $ oContext = null )
298
301
{
299
- $ context = new ReferenceContext (null , $ basePath );
300
302
if ($ baseDocument === null ) {
301
303
$ baseDocument = $ referencedDocument ;
302
304
}
303
305
304
306
foreach ($ referencedDocument as $ key => $ value ) {
305
307
// adjust reference URLs
306
308
if ($ key === '$ref ' && is_string ($ value )) {
309
+ $ fullPath = $ basePath . $ value ;
310
+ if (array_key_exists ($ fullPath , self ::$ relativeReferencesCache )) {
311
+ return self ::$ relativeReferencesCache [$ fullPath ];
312
+ }
313
+
307
314
if (isset ($ value [0 ]) && $ value [0 ] === '# ' ) {
308
315
// direcly inline references in the same document,
309
316
// these are not going to be valid in the new context anymore
@@ -315,8 +322,10 @@ private function adjustRelativeReferences($referencedDocument, $basePath, $baseD
315
322
$ this ->_recursingInsideFile = true ;
316
323
$ return = $ this ->adjustRelativeReferences ($ inlineDocument , $ basePath , $ baseDocument , $ oContext );
317
324
$ this ->_recursingInsideFile = false ;
325
+ self ::$ relativeReferencesCache [$ fullPath ] = $ return ;
318
326
return $ return ;
319
327
}
328
+ $ context = new ReferenceContext (null , $ basePath );
320
329
$ referencedDocument [$ key ] = $ context ->resolveRelativeUri ($ value );
321
330
$ parts = explode ('# ' , $ referencedDocument [$ key ], 2 );
322
331
if ($ parts [0 ] === $ oContext ->getUri ()) {
@@ -329,6 +338,7 @@ private function adjustRelativeReferences($referencedDocument, $basePath, $baseD
329
338
// adjust URLs for 'externalValue' references in Example Objects
330
339
// https://spec.openapis.org/oas/v3.0.3#example-object
331
340
if ($ key === 'externalValue ' && is_string ($ value )) {
341
+ $ context = new ReferenceContext (null , $ basePath );
332
342
$ referencedDocument [$ key ] = $ this ->makeRelativePath ($ oContext ->getUri (), $ context ->resolveRelativeUri ($ value ));
333
343
continue ;
334
344
}
0 commit comments