In dit artikel lees je hoe je Application Programming Interfaces (API's) opzet via Laravel en Fractal. 

API Development is een van de dingen waar we bij Codana sterk op inzetten. We bouwen graag sterke API's voor verschillende doeleinden.
Als we gebruik maken van Laravel voor het opbouwen van een applicatie maken we altijd gebruik van Fractal.

Er zijn tal van voorbeelden te vinden in de documentatie en op het internet hoe dit makkelijk te implementeren valt in Laravel.
We hebben hier een aantal "recommended practices" opgelijst, die we gebruiken in een aantal van onze eigen projecten.

Wat is Fractal voor Laravel?

Fractal is een library geschreven door de PHP League, een groep die open source framework-onafhankelijke libraries maakt. Om hier eenvoudig gebruik van te maken binnen Laravel-applicaties is er een wrapper voorzien.

Je gebruikt Fractal om consistente responses van je API terug te geven, om je data eenvoudig om te zetten naar JSON/YAML. Omdat je alles systematisch doorheen dezelfde transformers stuurt, zorg je er altijd voor dat data-types consistent hetzelfde zijn. Deze laag tussen je output en je data-modellen zorgt er voor dat schema wijzigingen niet automatisch mee door komen naar je API. Je bewaakt dus veel beter de backwards compatibility van je API.

Gebruik de injected service om responses op te bouwen.

Er zijn facades voorzien om dit eenvoudiger te maken, maar door dit zo te doen kan je IDE je helpen bij het opbouwen van je results.


public function __construct(Fractal $fractal)
{
	$this->fractal = $fractal;
}

public function respondWithData(User $user): JsonResponse
{
	return $this->fractal
      ->item($user)
      ->transformWith(new UserDetailsTransformer())
      ->respond();
}

 

Gebruik includes waar deze nuttig zijn en herbruik transformers.

Het is erg verleidelijk om specifieke responses op te bouwen door extra data mee te geven vanuit een specifieke transformer.
Om zo veel mogelijk consistente data te behouden naar de consumers van de API is het aangeraden om transformers te hergebruiken waar mogelijk.

->parseIncludes('user.emailSettings')

 

Extra data geef je door naar de constructor van de transformer.

Heb je extra data nodig in een transformer, dan kan je die meegeven naar de constructor.

Doe het dus niet op deze manier.

// The bad way.
$this->fractal
  ->item(['data' => $data, 'currentUser' => $user])
  ->transformWith(new DataForUserTransformer());


Het is duidelijker om dit te doen, je kan typehinten op `transform` in de DataForUserTransformer (op de twee argumenten).

// The better way.
$this->fractal->collection($data)
      ->transformWith(new DataForUserTransformer($user));

 

Gebruik een NullTransformer waar nodig.

Soms bouw je een endpoint op die niet strict restful is. Bijvoorbeeld een endpoint waar de gemiddeldes van verkoop van de voorbije week worden berekend. In zo'n gevallen kan je gebruik maken van een transformer die eenvoudig terug geeft wat je er in stopt, zonder dat je andere manieren van responses opbouwen nodig hebt.

final class NullTransformer extends TransformerAbstract
{
    public function transform(array $data): array
    {
        return $data;
    }
}

class Controller {

public function respondWithData(Request $request): JsonResponse
{
  $data = calculateForRequest($request);
  return $this->fractal
      ->item($data)
      ->transformWith(new NullTransformer())
      ->respond();
}
}

 

Eager loading is je beste vriend.

Als je Fractal zo hebt geconfigureerd dat er steeds een include nodig is, of op een andere manier related data getoond wordt, zorg er dan zeker voor dat die eager loaded zijn voor je die naar Fractal stuurt.

Het toevoegen van eager loading voor dat deze data naar Fractal gestuurd word, zorgt er voor dat die data al beschikbaar is in memory en niet per item nog eens uit de database gehaald moet worden. Dit zorgt voor gratis performantie winst voor deze endpoint.

Conclusie

Fractal zorgt er altijd voor dat je code een betere structuur heeft en dat je API consistent en eenvoudige te consumeren valt. Door gebruik te maken van deze tips kan je daar nog meer plezier aan beleven.