Skip to content

Commit

Permalink
Add a Performance guide for Server Timing (#25575)
Browse files Browse the repository at this point in the history
* Add a Performance guide for Server Timing

* Apply suggestions from code review

Co-authored-by: dawei-wang <[email protected]>

* Update files/en-us/web/api/performance_api/server_timing/index.md

Co-authored-by: dawei-wang <[email protected]>

* Add to landing page and groupdata

* Apply suggestions from @dipikabh

Co-authored-by: Dipika Bhattacharya <[email protected]>

* Review feedback from @wbamberg

---------

Co-authored-by: dawei-wang <[email protected]>
Co-authored-by: wbamberg <[email protected]>
Co-authored-by: Dipika Bhattacharya <[email protected]>
  • Loading branch information
4 people authored May 17, 2023
1 parent 90ba95c commit 3210ffb
Show file tree
Hide file tree
Showing 4 changed files with 93 additions and 2 deletions.
2 changes: 1 addition & 1 deletion files/en-us/web/api/performance_api/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ The following guides help you to understand key concepts of the Performance API
- [Resource timing](/en-US/docs/Web/API/Performance_API/Resource_timing): Measuring network timing for fetched resources, such as images, CSS, and JavaScript.
- [Navigation timing](/en-US/docs/Web/API/Performance_API/Navigation_timing): Measuring navigation timing of a document.
- [User timing](/en-US/docs/Web/API/Performance_API/User_timing): Measuring and recording performance data custom to your application.
- Server timing
- [Server timing](/en-US/docs/Web/API/Performance_API/Server_timing): Collecting server-side metrics.
- Paint timing
- Long task timing
- Largest contentful paint
Expand Down
79 changes: 79 additions & 0 deletions files/en-us/web/api/performance_api/server_timing/index.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
---
title: Server timing
slug: Web/API/Performance_API/Server_timing
page-type: guide
---

{{DefaultAPISidebar("Performance API")}}

Server-Timing is a part of the Performance API and allows servers to communicate metrics about the request-response cycle to the user agent. You can collect this information and act on server-side metrics in the same way as all the other metrics processed with the Performance API.

## Sending server metrics

The {{HTTPHeader("Server-Timing")}} HTTP header is used to surface any backend server timing metrics. For example, you might want to send database read/write operation times, CPU time, and file system access.

You can send metrics with or without values. The metrics can optionally contain a description. It is advised to keep names, descriptions, and data as short as possible to minimize the HTTP overhead.

Examples of `Server-Timing` headers:

```http
// Single metric without value
Server-Timing: missedCache
// Single metric with value
Server-Timing: cpu;dur=2.4
// Single metric with description and value
Server-Timing: cache;desc="Cache Read";dur=23.2
// Two metrics with values
Server-Timing: db;dur=53, app;dur=47.2
// Server-Timing as trailer
Trailer: Server-Timing
--- response body ---
Server-Timing: total;dur=123.4
```

To calculate real server-side metrics, consult the documentation of your server-side CMS, framework, or programming language for how to measure performance within the backend application. If your server uses Node.js, the performance measurement APIs will look very familiar to the Performance API in browsers. This is because the Node.js performance module is a subset of the W3C Web Performance APIs as well as additional APIs for Node.js-specific performance measurements. See the [Node.js performance documentation](https://nodejs.org/api/perf_hooks.html#performance-measurement-apis) for more information.

Note that there is no clock synchronization between the server, the client, and any intermediate proxies. This means that if your server sends timestamps or a `startTime`, the value might not meaningfully map to the {{domxref("PerformanceEntry.startTime", "startTime")}} of the client's timeline.

Once you have calculated your desired metrics, the server needs to send the `Server-Timing` header in its response. See the {{HTTPHeader("Server-Timing")}} reference page for an example of how to send the header in Node.js.

## Retrieving server metrics

The server timing metrics usually appear in the developer tools of the browser, but they are also stored as {{domxref("PerformanceServerTiming")}} performance entries that you can access like other [performance data](/en-US/docs/Web/API/Performance_API/Performance_data). However, there are no `"server-timing"` entries on their own. The `PerformanceServerTiming` objects are observable from `"navigation"` and `"resource"` performance entries. You access the server metrics from the {{domxref("PerformanceResourceTiming.serverTiming")}} property, which is an array of `PerformanceServerTiming` objects.

Given a {{HTTPHeader("Server-Timing")}} like this:

```
Server-Timing: cache;desc="Cache Read";dur=23.2,db;dur=53,app;dur=47.2
```

A `PerformanceObserver` can log the entries on the client side with the following code:

```js
const observer = new PerformanceObserver((list) => {
list.getEntries().forEach((entry) => {
entry.serverTiming.forEach((serverEntry) => {
console.log(
`${serverEntry.name} (${serverEntry.description}) duration: ${serverEntry.duration}`
);
// Logs "cache (Cache Read) duration: 23.2"
// Logs "db () duration: 53"
// Logs "app () duration: 47.2"
});
});
});

["navigation", "resource"].forEach((type) =>
observer.observe({ type, buffered: true })
);
```

## Privacy and security considerations

The `Server-Timing` header may expose potentially sensitive application and infrastructure information. Therefore, you need to control when the metrics are returned and to whom on the server side. For example, you could show metrics only to authenticated users and nothing to the public.

The `PerformanceServerTiming` interface is restricted to the same origin, but you can use the {{HTTPHeader("Timing-Allow-Origin")}} header to specify the domains that are allowed to access the server metrics. Also, note that this interface is only available in secure contexts (HTTPS) in some browsers.
11 changes: 11 additions & 0 deletions files/en-us/web/http/headers/server-timing/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,11 @@ The **`Server-Timing`** header communicates one or more metrics and descriptions

The syntax of the `Server-Timing` header allows you to communicate metrics in different ways: server metric name only, metric with value, metric with value and description, and metric with description.

This header can contain one or more metrics, separated by commas. Each metric has a name, an optional duration, and an optional description. These components are separated by semi-colons.

The duration component consists of the string `"dur"`, followed by `"="`, followed by the value, like `"dur=23.2"`.
The description component consists of the string `"desc"`, followed by `"="`, followed by the value, like `"desc=DB lookup"`.

The specification advises that names and descriptions should be kept as short as possible (use abbreviations and omit optional values where possible) to minimize the HTTP overhead.

```http
Expand Down Expand Up @@ -55,6 +60,12 @@ The `Server-Timing` header may expose potentially sensitive application and infr

In addition to having `Server-Timing` header metrics appear in the developer tools of the browser, the {{domxref("PerformanceServerTiming")}} interface enables tools to automatically collect and process metrics from JavaScript. This interface is restricted to the same origin, but you can use the {{HTTPHeader("Timing-Allow-Origin")}} header to specify the domains that are allowed to access the server metrics. The interface is only available in secure contexts (HTTPS) in some browsers.

The components of the `Server-Timing` header map to the {{domxref("PerformanceServerTiming")}} properties like this:

- `"name"` -> {{domxref("PerformanceServerTiming.name")}}
- `"dur"` -> {{domxref("PerformanceServerTiming.duration")}}
- `"desc"` -> {{domxref("PerformanceServerTiming.description")}}

## Specifications

{{Specifications}}
Expand Down
3 changes: 2 additions & 1 deletion files/jsondata/GroupData.json
Original file line number Diff line number Diff line change
Expand Up @@ -977,7 +977,8 @@
"/docs/Web/API/Performance_API/High_precision_timing",
"/docs/Web/API/Performance_API/Resource_timing",
"/docs/Web/API/Performance_API/Navigation_timing",
"/docs/Web/API/Performance_API/User_timing"
"/docs/Web/API/Performance_API/User_timing",
"/docs/Web/API/Performance_API/Server_timing"
],
"interfaces": [
"EventCounts",
Expand Down

0 comments on commit 3210ffb

Please sign in to comment.