---
title: Use friendly URLs
slug: cms-12/api/using-friendly-urls
docTags: 
createdAt: 2026-08-07T16:45:44.000Z
---

In addition to using the regular endpoints, `http://localhost:8080/api/episerver/v3.0/content/6`, you can use a friendly name URL of a specific content item for data query: `http://localhost:8080/en/alloy-plan/`.

To use a friendly name URL to retrieve data, set the Accept HTTP header to application/json in your request. You also need to enable this feature with:

```csharp
services
  .AddContentDeliveryApi()
  .WithFriendlyUrl();
```

You can apply this rule for acquiring “children” and “ancestors” of the content item. You can use `http://localhost:8080/en/alloy-plan/children` or `http://localhost:8080/en/alloy-plan/ancestors`.

The parameters for the request (such as expand) should be the same as before.

The following image shows the flow.

![](https://api.archbee.com/api/optimize/BrbvVORKJ5iIeSMZye5kI/gS2owz7Ix0cCGvOwkZUmW-20260722-175335.png "friendlyurls.png")

## Content Language

The language to get content is extracted from the URL. If it is empty, then the accept-language header is chosen.

Scenario:

1. Request to `http://localhost:8080/en` with accept-language header *sv*. The URL's language *en* is present, so it is chosen.
2. Request to `http://localhost:8080/` with accept-language header *sv*. The language is not present in the URL, so the language in the accept header is chosen, that is, *sv* in this case.

:::hint{type="info"}
**Note**
If the call to the Content Delivery API does not set the accept-language header (that is, the accept-language header is empty), as is the normal behavior of web browsers such as Chrome, it can automatically assign the value of the preferred language to accept-language (for example, en-US). The API then uses this value to query data.
:::

## Restrictions

- A partial router is used for this feature, and the type for incoming and outgoing routing is `IContent`.
  This can disrupt other partial routers in the site because the request URL is rewritten. To solve this problem:
  1. Create a class (for example, `CustomContentApiRouteService`) that inherits `ContentApiRouteService` and then register a transient life-cycled implementation for a `ContentApiRouteService` in the initialization service.
  2. Override the `ShouldRouteRequest` function to prevent the URL from being re-written in unexpected cases. For example, requests whose accept types contain application/JSON are currently handled by the partial router. So, you can add one more header (such as Routed-By-ContentApi) for CD-related requests and then use this header in the function to decide whether the partial router should handle the request and rewrite URL later on.
