Skip to content

Commit 1e28970

Browse files
authored
Better Fastify and Pino integration (#6663)
1 parent 598689c commit 1e28970

File tree

2 files changed

+66
-33
lines changed

2 files changed

+66
-33
lines changed

packages/web/docs/src/content/gateway/deployment/node-frameworks/fastify.mdx

Lines changed: 50 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -18,54 +18,71 @@ So you can benefit from the powerful plugins of Fastify ecosystem with Hive Gate
1818

1919
## Example
2020

21+
In order to connect Fastify's logger to the gateway, you need to install the
22+
`@graphql-hive/logger-pino` package together with `@graphql-hive/gateway-runtime` and `fastify`.
23+
24+
```sh npm2yarn
25+
npm i @graphql-hive/gateway-runtime @graphql-hive/logger-pino fastify
26+
```
27+
2128
```ts
22-
import fastify, { FastifyReply, FastifyRequest } from 'fastify'
29+
import fastify, { type FastifyReply, type FastifyRequest } from 'fastify'
2330
import { createGatewayRuntime } from '@graphql-hive/gateway-runtime'
31+
import { createLoggerFromPino } from '@graphql-hive/logger-pino'
32+
33+
// Request ID header used for tracking requests
34+
const requestIdHeader = 'x-request-id'
2435

2536
// This is the fastify instance you have created
26-
const app = fastify({ logger: true })
37+
const app = fastify({
38+
logger: true,
39+
// Use our custom request id header
40+
requestIdHeader,
41+
// Align with Hive Gateway's request id log label
42+
requestIdLogLabel: 'requestId',
43+
// Check the header first, then generate a new one if not found
44+
genReqId: (req): string =>
45+
req.headers[requestIdHeader]?.toString() || gw.fetchAPI.crypto.randomUUID()
46+
})
2747

28-
const serveRuntime = createGatewayRuntime<{
48+
// This will allow us to access Fastify request and reply objects in the gateway
49+
interface FastifyContext {
2950
req: FastifyRequest
3051
reply: FastifyReply
31-
}>({
32-
// Integrate Fastify logger
33-
logging: {
34-
debug: (...args) => args.forEach(arg => app.log.debug(arg)),
35-
info: (...args) => args.forEach(arg => app.log.info(arg)),
36-
warn: (...args) => args.forEach(arg => app.log.warn(arg)),
37-
error: (...args) => args.forEach(arg => app.log.error(arg))
38-
}
52+
}
53+
54+
const gateway = createGatewayRuntime<FastifyContext>({
55+
// Integrate Fastify's logger / Pino with the gateway logger
56+
logging: createLoggerFromPino(app.log),
57+
// Align with Fastify
58+
requestId: {
59+
// Use the same header name as Fastify
60+
headerName: requestIdHeader,
61+
// Use the request id from Fastify (see `FastifyContext`)
62+
generateRequestId: ({ context }) => context.req.id
63+
},
64+
// Point to the supergraph
65+
supergraph: './supergraph.graphql'
3966
})
4067

41-
/**
42-
* We pass the incoming HTTP request to Hive Gateway
43-
* and handle the response using Fastify's `reply` API
44-
* Learn more about `reply` https://www.fastify.io/docs/latest/Reply/
45-
**/
68+
// Bind the gateway to Fastify
4669
app.route({
47-
// Bind to the Hive Gateway's endpoint to avoid rendering on any path
48-
url: serveRuntime.graphqlEndpoint,
70+
// "*" is recommendeded in order to handle landing page, readiness and other related endpoints
71+
url: '*',
4972
method: ['GET', 'POST', 'OPTIONS'],
50-
handler: async (req, reply) => {
51-
// Second parameter adds Fastify's `req` and `reply` to the GraphQL Context
52-
const response = await serveRuntime.handleNodeRequestAndResponse(req, reply, {
53-
req,
54-
reply
55-
})
56-
response.headers.forEach((value, key) => {
57-
reply.header(key, value)
58-
})
59-
60-
reply.status(response.status)
73+
// Connect the gateway to Fastify route
74+
handler: (req, reply) => gateway.handleNodeRequestAndResponse(req, reply, { req, reply })
75+
})
6176

62-
reply.send(response.body)
77+
const port = 4000
6378

64-
return reply
79+
app.listen({ port, host: '0.0.0.0' }, err => {
80+
if (err) {
81+
console.error('Error starting gateway', err)
82+
process.exit(1)
6583
}
84+
console.log(`Gateway listening on port ${port}`)
6685
})
67-
68-
app.listen(4000)
6986
```
7087

7188
## Add dummy content type parser for File Uploads

packages/web/docs/src/content/gateway/logging-and-error-handling.mdx

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,7 @@ npm i winston @graphql-hive/winston
8282

8383
```ts
8484
import { createLogger, format, transports } from 'winston'
85+
import { defineConfig } from '@graphql-hive/gateway'
8586
import { createLoggerFromWinston } from '@graphql-hive/winston'
8687

8788
// Create a Winston logger
@@ -97,6 +98,21 @@ export const gatewayConfig = defineConfig({
9798
})
9899
```
99100

101+
### Integration with Pino (only Node.js)
102+
103+
Like Winston, you can also use [Pino](https://getpino.io/) with Hive Gateway on Node.js
104+
environments.
105+
106+
```ts
107+
import pino from 'pino'
108+
import { defineConfig } from '@graphql-hive/gateway'
109+
import { createLoggerFromPino } from '@graphql-hive/logger-pino'
110+
111+
export const gatewayConfig = defineConfig({
112+
logging: createLoggerFromPino(pino({ level: 'info' }))
113+
})
114+
```
115+
100116
### Custom Logger
101117

102118
If you want to implement your own logger, you can use the interface `Logger` from

0 commit comments

Comments
 (0)