@@ -154,8 +154,6 @@ private function setEmbeddedForResource(array &$data, array &$value, $propertyNa
154154 }
155155 }
156156 } else {
157- // print_r(func_get_args());
158- // die();
159157 $ data [$ propertyName ] = $ value ;
160158 }
161159 }
@@ -167,12 +165,19 @@ private function setEmbeddedForResource(array &$data, array &$value, $propertyNa
167165 * @param array $idValues
168166 * @param string $type
169167 */
170- private function addEmbeddedResourceLinks (array &$ data , $ propertyName , array &$ idProperties , array &$ idValues , $ type )
171- {
172- $ href = str_replace (
168+ private function addEmbeddedResourceLinks (
169+ array &$ data ,
170+ $ propertyName ,
171+ array &$ idProperties ,
172+ array &$ idValues ,
173+ $ type
174+ ) {
175+ $ href = self ::buildUrl (
176+ $ this ->mappings ,
173177 $ idProperties ,
174178 $ idValues ,
175- $ this ->mappings [$ type ]->getResourceUrl ()
179+ $ this ->mappings [$ type ]->getResourceUrl (),
180+ $ type
176181 );
177182
178183 if ($ href != $ this ->mappings [$ type ]->getResourceUrl ()) {
@@ -215,7 +220,10 @@ protected function getResponseAdditionalLinks(array $copy, $type)
215220 $ type
216221 );
217222
218- $ newOtherUrls = str_replace ($ idProperties , $ idValues , $ otherUrls );
223+ $ newOtherUrls = $ otherUrls ;
224+ foreach ($ newOtherUrls as &$ url ) {
225+ $ url = self ::buildUrl ($ this ->mappings , $ idProperties , $ idValues , $ url , $ type );
226+ }
219227
220228 if ($ newOtherUrls == $ otherUrls ) {
221229 return [];
@@ -247,7 +255,7 @@ private function getPropertyNameWithCurie($type, $propertyName)
247255 $ propertyName = sprintf (
248256 '%s:%s ' ,
249257 $ curie ['name ' ],
250- RecursiveFormatterHelper ::camelCaseToUnderscore ($ propertyName )
258+ self ::camelCaseToUnderscore ($ propertyName )
251259 );
252260 }
253261
@@ -261,12 +269,19 @@ private function getPropertyNameWithCurie($type, $propertyName)
261269 * @param array $idValues
262270 * @param string $type
263271 */
264- private function addEmbeddedResourceLinkToLinks (array &$ data , $ propertyName , array &$ idProperties , array &$ idValues , $ type )
265- {
266- $ href = str_replace (
272+ private function addEmbeddedResourceLinkToLinks (
273+ array &$ data ,
274+ $ propertyName ,
275+ array &$ idProperties ,
276+ array &$ idValues ,
277+ $ type
278+ ) {
279+ $ href = self ::buildUrl (
280+ $ this ->mappings ,
267281 $ idProperties ,
268282 $ idValues ,
269- $ this ->mappings [$ type ]->getResourceUrl ()
283+ $ this ->mappings [$ type ]->getResourceUrl (),
284+ $ type
270285 );
271286
272287 if ($ href != $ this ->mappings [$ type ]->getResourceUrl ()) {
@@ -329,18 +344,25 @@ private function isResourceInArray($inArrayValue)
329344 * @param string $inArrayProperty
330345 * @param array $inArrayValue
331346 */
332- private function addArrayValueResourceToEmbedded (array &$ data , $ propertyName , $ type , $ inArrayProperty , array &$ inArrayValue )
333- {
347+ private function addArrayValueResourceToEmbedded (
348+ array &$ data ,
349+ $ propertyName ,
350+ $ type ,
351+ $ inArrayProperty ,
352+ array &$ inArrayValue
353+ ) {
334354 list ($ idValues , $ idProperties ) = RecursiveFormatterHelper::getIdPropertyAndValues (
335355 $ this ->mappings ,
336356 $ inArrayValue ,
337357 $ type
338358 );
339359
340- $ href = str_replace (
360+ $ href = self ::buildUrl (
361+ $ this ->mappings ,
341362 $ idProperties ,
342363 $ idValues ,
343- $ this ->mappings [$ type ]->getResourceUrl ()
364+ $ this ->mappings [$ type ]->getResourceUrl (),
365+ $ type
344366 );
345367
346368 if ($ href != $ this ->mappings [$ type ]->getResourceUrl ()) {
@@ -395,4 +417,148 @@ private function setResponseMeta(array &$response)
395417 $ response [self ::META_KEY ] = $ this ->meta ;
396418 }
397419 }
420+
421+ /**
422+ * @param \NilPortugues\Api\Mapping\Mapping[] $mappings
423+ * @param $idProperties
424+ * @param $idValues
425+ * @param $url
426+ * @param $type
427+ *
428+ * @return mixed
429+ */
430+ private static function buildUrl (array &$ mappings , $ idProperties , $ idValues , $ url , $ type )
431+ {
432+ $ outputUrl = str_replace ($ idProperties , $ idValues , $ url );
433+ if ($ outputUrl !== $ url ) {
434+ return $ outputUrl ;
435+ }
436+
437+ $ outputUrl = self ::secondPassBuildUrl ([$ mappings [$ type ]->getClassAlias ()], $ idValues , $ url );
438+
439+ if ($ outputUrl !== $ url ) {
440+ return $ outputUrl ;
441+ }
442+
443+ $ className = $ mappings [$ type ]->getClassName ();
444+ $ className = explode ('\\' , $ className );
445+ $ className = array_pop ($ className );
446+
447+ $ outputUrl = self ::secondPassBuildUrl ([$ className ], $ idValues , $ url );
448+ if ($ outputUrl !== $ url ) {
449+ return $ outputUrl ;
450+ }
451+
452+ return $ url ;
453+ }
454+
455+ /**
456+ * @param $idPropertyName
457+ * @param $idValues
458+ * @param $url
459+ *
460+ * @return mixed
461+ */
462+ private static function secondPassBuildUrl ($ idPropertyName , $ idValues , $ url )
463+ {
464+ if (!empty ($ idPropertyName )) {
465+ $ outputUrl = self ::toCamelCase ($ idPropertyName , $ idValues , $ url );
466+ if ($ url !== $ outputUrl ) {
467+ return $ outputUrl ;
468+ }
469+
470+ $ outputUrl = self ::toLowerFirstCamelCase ($ idPropertyName , $ idValues , $ url );
471+ if ($ url !== $ outputUrl ) {
472+ return $ outputUrl ;
473+ }
474+
475+ $ outputUrl = self ::toUnderScore ($ idPropertyName , $ idValues , $ url );
476+ if ($ url !== $ outputUrl ) {
477+ return $ outputUrl ;
478+ }
479+ }
480+
481+ return $ url ;
482+ }
483+
484+ /**
485+ * @param $original
486+ * @param $idValues
487+ * @param $url
488+ *
489+ * @return mixed
490+ */
491+ private static function toCamelCase ($ original , $ idValues , $ url )
492+ {
493+ foreach ($ original as &$ o ) {
494+ $ o = '{ ' .self ::underscoreToCamelCase (self ::camelCaseToUnderscore ($ o )).'} ' ;
495+ }
496+
497+ return str_replace ($ original , $ idValues , $ url );
498+ }
499+
500+ /**
501+ * @param $original
502+ * @param $idValues
503+ * @param $url
504+ *
505+ * @return mixed
506+ */
507+ private static function toLowerFirstCamelCase ($ original , $ idValues , $ url )
508+ {
509+ foreach ($ original as &$ o ) {
510+ $ o = self ::underscoreToCamelCase (self ::camelCaseToUnderscore ($ o ));
511+ $ o [0 ] = strtolower ($ o [0 ]);
512+ $ o = '{ ' .$ o .'} ' ;
513+ }
514+
515+ return str_replace ($ original , $ idValues , $ url );
516+ }
517+
518+ /**
519+ * @param $original
520+ * @param $idValues
521+ * @param $url
522+ *
523+ * @return mixed
524+ */
525+ private static function toUnderScore ($ original , $ idValues , $ url )
526+ {
527+ foreach ($ original as &$ o ) {
528+ $ o = '{ ' .self ::camelCaseToUnderscore ($ o ).'} ' ;
529+ }
530+
531+ return str_replace ($ original , $ idValues , $ url );
532+ }
533+
534+ /**
535+ * Transforms a given string from camelCase to under_score style.
536+ *
537+ * @param string $camel
538+ * @param string $splitter
539+ *
540+ * @return string
541+ */
542+ private static function camelCaseToUnderscore ($ camel , $ splitter = '_ ' )
543+ {
544+ $ camel = preg_replace (
545+ '/(?!^)[[:upper:]][[:lower:]]/ ' ,
546+ '$0 ' ,
547+ preg_replace ('/(?!^)[[:upper:]]+/ ' , $ splitter .'$0 ' , $ camel )
548+ );
549+
550+ return strtolower ($ camel );
551+ }
552+
553+ /**
554+ * Converts a underscore string to camelCase.
555+ *
556+ * @param string $string
557+ *
558+ * @return string
559+ */
560+ private static function underscoreToCamelCase ($ string )
561+ {
562+ return str_replace (' ' , '' , ucwords (strtolower (str_replace (['_ ' , '- ' ], ' ' , $ string ))));
563+ }
398564}
0 commit comments