Developer Journal

Intermediate · 10 minute read

Creating Custom REST Endpoints

Secure Drupal endpoints with explicit routes, authentication, serialization, validation, and cache policy.

Last updated August 6, 2026

A custom endpoint is an external contract. Its status codes, authentication, validation, cache headers, and error format deserve the same design attention as its successful payload.

Start with the contract

Document method, route, authentication, request schema, response schema, errors, and versioning. Prefer core entity APIs when they already expose the required contract.

Enforce access at multiple layers

Route permissions establish the first gate; entity access and field access still apply. Validate content types, sizes, and allowed values before invoking domain behavior. Never trust a client-supplied entity identifier by itself.

Return deliberate responses

Use JSON responses with appropriate status codes and cacheability. Avoid leaking exception details. For writes, consider idempotency and concurrency behavior.

Working example

public function status(int $job): CacheableJsonResponse {
  $result = $this->jobs->status($job);
  $response = new CacheableJsonResponse(['data' => $result]);
  $response->addCacheableDependency($result);
  return $response;
}

Key Takeaways

  • Design the HTTP contract before the controller.
  • Check route, entity, and field access.
  • Return intentional errors and cache policy.

Further Reading