File
To access files from your request, you can use the File parameter to consume it as a stream or SavedFile to pump the file to disk and return a filepath.
WARNING
Requests with files are not supported in routes of type GET.
INFO
This parameter automatically registers @fastify/multipart in your Fastify instance.
You can further configure the plugin by passing fastifyMultipart to the Kita plugin options.
Prerequisites
Before using the File parameter, you need to add the ajvFilePlugin from @fastify/multipart when creating your Fastify instance.
import { ajvFilePlugin } from '@fastify/multipart';
import fastify from 'fastify';
const app = fastify({
ajv: { plugins: [ajvFilePlugin] } // [!code ++]
});The above plugin registers the isFile keyword in the AJV instance, which is used to validate the file parameter.
If you encounter the following error, it’s because the ajvFilePlugin was not registered in your Fastify instance:
FastifyError [Error]: Failed building the validation schema for
<METHOD>:<URL>, due to error strict mode: unknown keyword: “isFile”
Usage
import type { File } from '@kitajs/runtime';
import { createWriteStream } from 'node:fs';
import { createBrotliCompress } from 'node:zlib';
export async function post(file: File) {
await file.file
// Do whatever you need to do with the file
// For exemple, compress it and save it to disk
.pipe(createBrotliCompress())
.pipe(createWriteStream(file.filename + '.br'));
return true;
}{
"paths": {
"/": {
"post": {
"operationId": "postIndex",
"requestBody": {
"content": {
"multipart/form-data": {
"schema": {
"properties": {
"file": {
"type": "string",
"format": "binary"
}
},
"required": ["file"],
"type": "object"
}
}
},
"required": true
},
"responses": {
"2XX": {
"description": "Default Response",
"content": {
"application/json": { "schema": { "type": "boolean" } }
}
}
}
}
}
}
}2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
You can also use the SavedFile type to save the file to disk and return the path to the file.
import type { SavedFile } from '@kitajs/runtime';
export function post(file: SavedFile) {
return `File saved at ${file.filepath}!`;
}{
"paths": {
"/": {
"post": {
"operationId": "postIndex",
"requestBody": {
"content": {
"multipart/form-data": {
"schema": {
"properties": {
"file": {
"type": "string",
"format": "binary"
}
},
"required": ["file"],
"type": "object"
}
}
},
"required": true
},
"responses": {
"2XX": {
"description": "Default Response",
"content": {
"application/json": { "schema": { "type": "string" } }
}
}
}
}
}
}
}2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
Custom names
You can also use dedicated names for the file and the field name.
import type { File, SavedFile } from '@kitajs/runtime';
export function post(
anything: File<'avatar'>,
anythingElse: SavedFile<'background'>
) {
return true;
}{
"paths": {
"/": {
"post": {
"operationId": "postIndex",
"requestBody": {
"content": {
"multipart/form-data": {
"schema": {
"properties": {
"avatar": {
"type": "string",
"format": "binary"
},
"background": {
"type": "string",
"format": "binary"
}
},
"required": ["avatar", "background"],
"type": "object"
}
}
},
"required": true
},
"responses": {
"2XX": {
"description": "Default Response",
"content": {
"application/json": { "schema": { "type": "boolean" } }
}
}
}
}
}
}
}2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38