Aktueller Stand

This commit is contained in:
2026-01-22 19:05:45 +01:00
parent 85dee61a4d
commit e280e4eadb
1967 changed files with 397327 additions and 74093 deletions

View File

@@ -1,21 +1,18 @@
<h1 align="center">Fastify</h1>
## Plugins
Fastify allows the user to extend its functionalities with plugins. A plugin can
be a set of routes, a server [decorator](./Decorators.md), or whatever. The API
that you will need to use one or more plugins, is `register`.
Fastify can be extended with plugins, which can be a set of routes, a server
[decorator](./Decorators.md), or other functionality. Use the `register` API to
add one or more plugins.
By default, `register` creates a *new scope*, this means that if you make some
changes to the Fastify instance (via `decorate`), this change will not be
reflected by the current context ancestors, but only by its descendants. This
feature allows us to achieve plugin *encapsulation* and *inheritance*, in this
way we create a *directed acyclic graph* (DAG) and we will not have issues
caused by cross dependencies.
By default, `register` creates a *new scope*, meaning changes to the Fastify
instance (via `decorate`) will not affect the current context ancestors, only
its descendants. This feature enables plugin *encapsulation* and *inheritance*,
creating a *directed acyclic graph* (DAG) and avoiding cross-dependency issues.
You may have already seen in the [Getting
Started](../Guides/Getting-Started.md#your-first-plugin) guide how easy it is
to use this API:
```
The [Getting Started](../Guides/Getting-Started.md#your-first-plugin) guide
includes an example of using this API:
```js
fastify.register(plugin, [options])
```
@@ -33,10 +30,9 @@ Fastify specific options is:
+ [`logSerializers`](./Routes.md#custom-log-serializer)
+ [`prefix`](#route-prefixing-option)
**Note: Those options will be ignored when used with fastify-plugin**
These options will be ignored when used with fastify-plugin.
It is possible that Fastify will directly support other options in the future.
Thus, to avoid collisions, a plugin should consider namespacing its options. For
To avoid collisions, a plugin should consider namespacing its options. For
example, a plugin `foo` might be registered like so:
```js
@@ -49,8 +45,7 @@ fastify.register(require('fastify-foo'), {
})
```
If collisions are not a concern, the plugin may simply accept the options object
as-is:
If collisions are not a concern, the plugin may accept the options object as-is:
```js
fastify.register(require('fastify-foo'), {
@@ -60,9 +55,8 @@ fastify.register(require('fastify-foo'), {
})
```
The `options` parameter can also be a `Function` that will be evaluated at the
time the plugin is registered while giving access to the Fastify instance via
the first positional argument:
The `options` parameter can also be a `Function` evaluated at plugin registration,
providing access to the Fastify instance via the first argument:
```js
const fp = require('fastify-plugin')
@@ -77,40 +71,38 @@ fastify.register(fp((fastify, opts, done) => {
fastify.register(require('fastify-foo'), parent => parent.foo_bar)
```
The Fastify instance passed on to the function is the latest state of the
**external Fastify instance** the plugin was declared on, allowing access to
variables injected via [`decorate`](./Decorators.md) by preceding plugins
according to the **order of registration**. This is useful in case a plugin
depends on changes made to the Fastify instance by a preceding plugin i.e.
utilizing an existing database connection to wrap around it.
The Fastify instance passed to the function is the latest state of the **external
Fastify instance** the plugin was declared on, allowing access to variables
injected via [`decorate`](./Decorators.md) by preceding plugins according to the
**order of registration**. This is useful if a plugin depends on changes made to
the Fastify instance by a preceding plugin, such as utilizing an existing database
connection.
Keep in mind that the Fastify instance passed on to the function is the same as
the one that will be passed into the plugin, a copy of the external Fastify
instance rather than a reference. Any usage of the instance will behave the same
as it would if called within the plugins function i.e. if `decorate` is called,
the decorated variables will be available within the plugins function unless it
was wrapped with [`fastify-plugin`](https://github.com/fastify/fastify-plugin).
Keep in mind that the Fastify instance passed to the function is the same as the
one passed into the plugin, a copy of the external Fastify instance rather than
a reference. Any usage of the instance will behave the same as it would if called
within the plugin's function. For example, if `decorate` is called, the decorated
variables will be available within the plugin's function unless it was wrapped
with [`fastify-plugin`](https://github.com/fastify/fastify-plugin).
#### Route Prefixing option
<a id="route-prefixing-option"></a>
If you pass an option with the key `prefix` with a `string` value, Fastify will
use it to prefix all the routes inside the register, for more info check
If an option with the key `prefix` and a `string` value is passed, Fastify will
use it to prefix all the routes inside the register. For more info, check
[here](./Routes.md#route-prefixing).
Be aware that if you wrap your routes with
Be aware that if routes are wrapped with
[`fastify-plugin`](https://github.com/fastify/fastify-plugin), this option will
not work (there is a [workaround](./Routes.md#fastify-plugin) available).
not work (see the [workaround](./Routes.md#fastify-plugin)).
#### Error handling
<a id="error-handling"></a>
The error handling is done by
[avvio](https://github.com/mcollina/avvio#error-handling).
Error handling is done by [avvio](https://github.com/mcollina/avvio#error-handling).
As a general rule, it is highly recommended that you handle your errors in the
next `after` or `ready` block, otherwise you will get them inside the `listen`
callback.
As a general rule, handle errors in the next `after` or `ready` block, otherwise
they will be caught inside the `listen` callback.
```js
fastify.register(require('my-plugin'))
@@ -145,16 +137,15 @@ await fastify.ready()
await fastify.listen({ port: 3000 })
```
*Note: Using `await` when registering a plugin loads the plugin
and the underlying dependency tree, "finalizing" the encapsulation process.
Any mutations to the plugin after it and its dependencies have been
loaded will not be reflected in the parent instance.*
Using `await` when registering a plugin loads the plugin and its dependencies,
"finalizing" the encapsulation process. Any mutations to the plugin after it and
its dependencies have been loaded will not be reflected in the parent instance.
#### ESM support
<a id="esm-support"></a>
ESM is supported as well from [Node.js
`v13.3.0`](https://nodejs.org/api/esm.html) and above!
ESM is supported from [Node.js `v13.3.0`](https://nodejs.org/api/esm.html)
and above.
```js
// main.mjs
@@ -179,21 +170,29 @@ export default plugin
### Create a plugin
<a id="create-plugin"></a>
Creating a plugin is very easy, you just need to create a function that takes
three parameters, the `fastify` instance, an `options` object, and the `done`
callback.
Creating a plugin is easy. Create a function that takes three parameters: the
`fastify` instance, an `options` object, and the `done` callback. Alternatively,
use an `async` function and omit the `done` callback.
Example:
```js
module.exports = function (fastify, opts, done) {
module.exports = function callbackPlugin (fastify, opts, done) {
fastify.decorate('utility', function () {})
fastify.get('/', handler)
done()
}
// Or using async
module.exports = async function asyncPlugin (fastify, opts) {
fastify.decorate('utility', function () {})
fastify.get('/', handler)
}
```
You can also use `register` inside another `register`:
`register` can also be used inside another `register`:
```js
module.exports = function (fastify, opts, done) {
fastify.decorate('utility', function () {})
@@ -205,28 +204,23 @@ module.exports = function (fastify, opts, done) {
done()
}
```
Sometimes, you will need to know when the server is about to close, for example,
because you must close a connection to a database. To know when this is going to
happen, you can use the [`'onClose'`](./Hooks.md#on-close) hook.
Do not forget that `register` will always create a new Fastify scope, if you do
not need that, read the following section.
Remember, `register` always creates a new Fastify scope. If this is not needed,
read the following section.
### Handle the scope
<a id="handle-scope"></a>
If you are using `register` only for extending the functionality of the server
with [`decorate`](./Decorators.md), it is your responsibility to tell Fastify
not to create a new scope. Otherwise, your changes will not be accessible by the
user in the upper scope.
If `register` is used only to extend server functionality with
[`decorate`](./Decorators.md), tell Fastify not to create a new scope. Otherwise,
changes will not be accessible in the upper scope.
You have two ways to tell Fastify to avoid the creation of a new context:
There are two ways to avoid creating a new context:
- Use the [`fastify-plugin`](https://github.com/fastify/fastify-plugin) module
- Use the `'skip-override'` hidden property
We recommend using the `fastify-plugin` module, because it solves this problem
for you, and you can pass a version range of Fastify as a parameter that your
plugin will support.
Using the `fastify-plugin` module is recommended, as it solves this problem and
allows passing a version range of Fastify that the plugin will support:
```js
const fp = require('fastify-plugin')
@@ -238,10 +232,9 @@ module.exports = fp(function (fastify, opts, done) {
Check the [`fastify-plugin`](https://github.com/fastify/fastify-plugin)
documentation to learn more about how to use this module.
If you do not use the `fastify-plugin` module, you can use the `'skip-override'`
hidden property, but we do not recommend it. If in the future the Fastify API
changes it will be your responsibility to update the module, while if you use
`fastify-plugin`, you can be sure about backward compatibility.
If not using `fastify-plugin`, the `'skip-override'` hidden property can be used,
but it is not recommended. Future Fastify API changes will be your responsibility
to update, whilst `fastify-plugin` ensures backward compatibility.
```js
function yourPlugin (fastify, opts, done) {
fastify.decorate('utility', function () {})