Multipartuploads met Multer-interceptors
Configureer FileInterceptor en FilesInterceptor voor uploads van één of meerdere bestanden met groottelimieten.
Multipartuploads met Multer-interceptors is een gratis Enterprise-backend-API's met NestJS-les op CoddyKit. Dit is les 1 van 4. Je kunt de volledige les hieronder gratis lezen en daarna in de browser praktisch oefenen met een ingebouwde code-editor en een AI-begeleider die 24/7 beschikbaar is. Deze les maakt deel uit van het leertraject Enterprise-backend-API's met NestJS. Je voortgang wordt gesynchroniseerd op het web en in de CoddyKit-app. De cursus Enterprise-backend-API's met NestJS bevat in totaal 4 lessen.
Waarom Multer voor uploads
HTTP-bestandsuploads gebruiken het inhoudstype multipart/form-data, dat de aanvraagbody opsplitst in delen: tekstvelden en binaire bestandsgegevens, gescheiden door een grensmarkering.
NestJS parseert deze indeling niet zelfstandig. In plaats daarvan levert het directe wrappers rond Multer, de de-factostandaard-Express-middleware voor het parsen van multipart-gegevens. U gebruikt Multer via interceptors in plaats van middleware handmatig te configureren.
FileInterceptor— één bestand uit één veldFilesInterceptor— meerdere bestanden uit één veldFileFieldsInterceptor— bestanden uit meerdere benoemde velden
Deze les richt zich op de eerste twee en op het afdwingen van groottelimieten.
De typen installeren
De interceptors bevinden zich in @nestjs/platform-express, dat al aanwezig is in een standaard-Nest-app. U hebt alleen de typedefinities van Multer nodig om de parameters van uw handler correct te typeren.
Installeer de ontwikkelafhankelijkheid zodat Express.Multer.File door TypeScript wordt herkend:
npm install -D @types/multer
// Now Express.Multer.File is available globally in TypeScript.
// It describes the in-memory/disk file object Multer attaches
// to the request, e.g. originalname, mimetype, size, buffer, path.Eén bestand met FileInterceptor
Koppel FileInterceptor('field') aan @UseInterceptors. De tekenreeks is de naam van het form-data-veld dat het bestand bevat. Lees het geparseerde bestand vervolgens met de decorator @UploadedFile().
De gedecoreerde parameter is één Express.Multer.File. Let op: de parameternaam in het formulier hoeft niet overeen te komen met het argument van de handler — alleen de veldtekenreeks van de interceptor is van belang.
import { Controller, Post, UploadedFile, UseInterceptors } from '@nestjs/common';
import { FileInterceptor } from '@nestjs/platform-express';
@Controller('avatars')
export class AvatarsController {
@Post()
@UseInterceptors(FileInterceptor('avatar'))
upload(@UploadedFile() file: Express.Multer.File) {
return {
name: file.originalname,
type: file.mimetype,
size: file.size,
};
}
}Opslag in geheugen tegenover schijfopslag
Standaard gebruikt Multer opslag in het geheugen: het volledige bestand komt in file.buffer terecht als Buffer. Dat is handig om het bestand door te sturen naar S3 of in het proces te verwerken, maar grote bestanden kunnen het RAM uitputten.
Gebruik voor lokale opslag schijfopslag. Multer schrijft het bestand dan naar een pad en geeft u file.path in plaats van een buffer. Geef opties door als tweede argument van de interceptor.
import { diskStorage } from 'multer';
import { extname } from 'path';
import { randomUUID } from 'crypto';
export const imageStorage = diskStorage({
destination: './uploads/images',
filename: (_req, file, cb) => {
const unique = randomUUID();
cb(null, `${unique}${extname(file.originalname)}`);
},
});
// Usage:
// @UseInterceptors(FileInterceptor('photo', { storage: imageStorage }))Een groottelimiet afdwingen
Vertrouw nooit op groottes die door de client zijn opgegeven. Beperk het aantal bytes dat Multer accepteert via de optie limits.fileSize (in bytes). Wanneer een bestand deze limiet overschrijdt, breekt Multer af en geeft Nest een fout in de stijl van 413 voordat uw handler wordt uitgevoerd.
Combineer fileSize met files om ook het aantal bestanden in een meervoudige upload te beperken.
import { FileInterceptor } from '@nestjs/platform-express';
const FIVE_MB = 5 * 1024 * 1024;
@Post('avatar')
@UseInterceptors(
FileInterceptor('avatar', {
limits: { fileSize: FIVE_MB },
}),
)
upload(@UploadedFile() file: Express.Multer.File) {
return { stored: file.originalname };
}Limieten veilig berekenen
Express-limieten worden uitgedrukt in ruwe bytes, wat gemakkelijk een factor tien verkeerd kan uitpakken. Een kleine pure hulpfunctie houdt de berekening expliciet en testbaar en kan overal zonder framework worden uitgevoerd.
Hieronder zet mb megabytes om naar bytes en controleren we een voorgestelde uploadgrootte tegen een limiet.
function mb(n: number): number {
return n * 1024 * 1024;
}
function withinLimit(sizeBytes: number, capMb: number): boolean {
return sizeBytes <= mb(capMb);
}
const FILE_CAP_MB = 5;
console.log('5MB in bytes:', mb(FILE_CAP_MB));
console.log(withinLimit(mb(4), FILE_CAP_MB)); // true
console.log(withinLimit(mb(6), FILE_CAP_MB)); // false
console.log(withinLimit(5_242_880, FILE_CAP_MB)); // true (exactly 5MB)Meerdere bestanden met FilesInterceptor
FilesInterceptor('field', maxCount, options) accepteert meerdere bestanden die onder dezelfde veldnaam zijn verzonden. Lees ze met @UploadedFiles(), dat een array oplevert.
Het argument maxCount is een harde bovengrens voor het aantal bestanden dat Nest verzamelt; extra bestanden veroorzaken een fout. Combineer dit met limits.fileSize voor een limiet in bytes per bestand.
import { Controller, Post, UploadedFiles, UseInterceptors } from '@nestjs/common';
import { FilesInterceptor } from '@nestjs/platform-express';
@Controller('gallery')
export class GalleryController {
@Post()
@UseInterceptors(
FilesInterceptor('photos', 10, {
limits: { fileSize: 5 * 1024 * 1024 },
}),
)
upload(@UploadedFiles() files: Express.Multer.File[]) {
return files.map((f) => ({ name: f.originalname, size: f.size }));
}
}Filteren op MIME-type
Groottelimieten verhinderen niet dat het verkeerde bestandstype wordt geüpload. Gebruik fileFilter om elk deel tijdens het streamen te accepteren of te weigeren. Roep de callback aan met (null, true) om een bestand te behouden, of met een fout om het te weigeren.
Weigeren met een BadRequestException levert een nette 400 op in plaats van een algemene fout.
import { BadRequestException } from '@nestjs/common';
import { Request } from 'express';
export function imageFileFilter(
_req: Request,
file: Express.Multer.File,
cb: (error: Error | null, accept: boolean) => void,
) {
const allowed = ['image/png', 'image/jpeg', 'image/webp'];
if (!allowed.includes(file.mimetype)) {
return cb(new BadRequestException('Only PNG, JPEG, or WebP allowed'), false);
}
cb(null, true);
}Valideren met ParseFilePipe
De ingebouwde ParseFilePipe van Nest valideert het al geparseerde bestand declaratief in de handler. De pipe combineert validators zoals MaxFileSizeValidator en FileTypeValidator en retourneert 422 wanneer ze falen.
Dit vormt een aanvulling op Multers limits: Multer bewaakt de stream, terwijl de pipe uw bedrijfsregels bewaakt en duidelijkere foutmeldingen geeft.
import {
ParseFilePipe,
MaxFileSizeValidator,
FileTypeValidator,
UploadedFile,
} from '@nestjs/common';
@Post('avatar')
@UseInterceptors(FileInterceptor('avatar'))
upload(
@UploadedFile(
new ParseFilePipe({
validators: [
new MaxFileSizeValidator({ maxSize: 5 * 1024 * 1024 }),
new FileTypeValidator({ fileType: /(png|jpe?g|webp)$/ }),
],
}),
)
file: Express.Multer.File,
) {
return { ok: true, name: file.originalname };
}Configuratie centraliseren met een fabriek
Opslag, limieten en filters op elke route herhalen leidt gemakkelijk tot fouten. Haal één object MulterOptions (of een fabriek) uit en hergebruik het. Enterprise-apps registreren standaardwaarden vaak globaal via MulterModule.register() en overschrijven ze alleen per route wanneer dat nodig is.
Zo blijven limieten consistent en kunt u een limiet met één regel verhogen.
import { MulterOptions } from '@nestjs/platform-express/multer/interfaces/multer-options.interface';
import { diskStorage } from 'multer';
import { imageFileFilter } from './image-file.filter';
export const imageUploadOptions: MulterOptions = {
storage: diskStorage({ destination: './uploads/images' }),
limits: { fileSize: 5 * 1024 * 1024, files: 10 },
fileFilter: imageFileFilter,
};
// @UseInterceptors(FilesInterceptor('photos', 10, imageUploadOptions))De fout voor de groottelimiet afhandelen
Wanneer limits.fileSize wordt overschreden, genereert Multer een fout waarvan code gelijk is aan 'LIMIT_FILE_SIZE'. Standaard pakt Nest deze fout in, maar u kunt deze met een uitzonderingsfilter omzetten in een gebruiksvriendelijke payload, zodat clients een duidelijke, consistente melding ontvangen.
Het vertalen van codes op laag niveau van Multer naar HTTP-antwoorden is kenmerkend voor upload-eindpunten van productiekwaliteit.
import { ExceptionFilter, Catch, ArgumentsHost, HttpStatus } from '@nestjs/common';
import { MulterError } from 'multer';
import { Response } from 'express';
@Catch(MulterError)
export class MulterExceptionFilter implements ExceptionFilter {
catch(err: MulterError, host: ArgumentsHost) {
const res = host.switchToHttp().getResponse<Response>();
const status =
err.code === 'LIMIT_FILE_SIZE'
? HttpStatus.PAYLOAD_TOO_LARGE
: HttpStatus.BAD_REQUEST;
res.status(status).json({ statusCode: status, message: err.message });
}
}Korte toets
Toets uw begrip van het kiezen van de juiste interceptor en het lezen van het resultaat ervan.
Samenvatting
U kunt nu multipart-uploads van begin tot eind in NestJS configureren:
- FileInterceptor('field', options) +
@UploadedFile()voor één bestand. - FilesInterceptor('field', maxCount, options) +
@UploadedFiles()voor meerdere bestanden onder één veld. - limits.fileSize (bytes) beperkt de streamgrootte; limits.files beperkt het aantal bestanden; fileFilter weigert onjuiste MIME-typen vroegtijdig.
- diskStorage tegenover opslag in het geheugen bepaalt of u
file.pathoffile.bufferkrijgt. - ParseFilePipe met
MaxFileSizeValidator/FileTypeValidatorvalideert declaratief, en een filter voor MulterError zetLIMIT_FILE_SIZEom naar een nette 413.
Centraliseer deze opties in één fabriek, zodat limieten consistent blijven voor elke uploadroute.
Leer TypeScript met een AI-tutor — gratis
Schrijf echte code en voer die uit in je browser, krijg direct hulp van een AI-tutor die 24/7 beschikbaar is en ga verder waar je gebleven bent op het web of in de app.
- Cursussen
- 20
- Lessen
- 76
Veelgestelde vragen
Is de les “Multipartuploads met Multer-interceptors” gratis?
Ja — de volledige tekst van “Multipartuploads met Multer-interceptors” kun je hier gratis op het web lezen. Als je interactief wilt oefenen met een ingebouwde code-editor en een AI-begeleider die 24/7 beschikbaar is, en de rest van de cursus Enterprise-backend-API's met NestJS wilt ontgrendelen, kun je upgraden naar CoddyKit PRO. De cursus Enterprise-backend-API's met NestJS bevat in totaal 4 lessen.
Wat leer ik in “Multipartuploads met Multer-interceptors”?
Configureer FileInterceptor en FilesInterceptor voor uploads van één of meerdere bestanden met groottelimieten. Je oefent met Enterprise-backend-API's met NestJS door code rechtstreeks in de browser uit te voeren. Een AI-begeleider die 24/7 beschikbaar is beantwoordt je vragen terwijl je de les doorwerkt.
Heb ik ervaring nodig om met Enterprise-backend-API's met NestJS te beginnen?
Ervaring vooraf is niet nodig. Enterprise-backend-API's met NestJS op CoddyKit is opgebouwd voor beginners tot gevorderden, zodat je hier of bij het begin kunt starten en in je eigen tempo kunt leren. Dit is les 1 van 4.
Hoe lang duurt de les “Multipartuploads met Multer-interceptors”?
De meeste lessen van CoddyKit duren ongeveer 5–10 minuten. Elke les is kort en interactief, zodat je gestaag vooruitgaat en op het web en in de app precies verdergaat waar je was gebleven.
Kan ik code schrijven en uitvoeren in deze les over Enterprise-backend-API's met NestJS?
Ja. Elke les over Enterprise-backend-API's met NestJS bevat een ingebouwde code-editor, zodat je rechtstreeks in je browser echte code kunt schrijven en uitvoeren en direct feedback van AI krijgt — lokale installatie is niet nodig.
Alle lessen in deze cursus
- Multipartuploads met Multer-interceptors
- Grote responses streamen met StreamableFile
- Rechtstreekse S3-uploads met presigned URL's
- Pijplijnen voor beeldverwerking met Sharp