Skip to content

Commit 72a6ba4

Browse files
author
Nil Portugués
committed
Fixing shortcomings with the link generation.
1 parent aa675e3 commit 72a6ba4

File tree

2 files changed

+438
-16
lines changed

2 files changed

+438
-16
lines changed

src/HalJsonTransformer.php

Lines changed: 182 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -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

Comments
 (0)