Fastify fails to register middleware when using the decorate method

In the process of crafting middleware for scrutinizing the JWT transmitted during route invocations, I meticulously adhered to the guidelines stipulated in the JWT middleware manual and ported the code to TypeScript from vanilla JS. Regrettably, an anomaly arises where fastify.decorate fails to acknowledge the newly designed decorator earmarked for invocation on requests.

authMiddleware.ts

import fp from "fastify-plugin";
import fastifyJwt from "@fastify/jwt";
import { FastifyInstance, FastifyRequest, FastifyReply } from "fastify";

const authenticatePlugin = fp<FastifyInstance>(async (fastify, opts) => {
  fastify.register(fastifyJwt, {
    secret: "secret",
  });

  fastify.decorate(
    "authenticate",
    async (request: FastifyRequest, reply: FastifyReply) => {
      try {
        await request.jwtVerify();
      } catch (err) {
        reply.send(err);
      }
    }
  );
});

export default authenticatePlugin;

Index.ts(entry point to api)

const server = fastify({
  logger: pino({ level: "info" }),
});

server.register(authenticatePlugin);
server.register(db, { uri });
server.register(MatchRoute);
server.register(AuthRoutes);

const start = async () => {
  try {
    await server.listen({ port: 7000 });
    console.log("Server started successfully");
  } catch (err) {
    server.log.error(err);
    process.exit(1);
  }
};
start();

The root cause is pinpointed within my route:

  fastify.post<{ Body: MatchAttributes }>(
    "/matches",
    {
      onRequest: [fastify.authenticate],
    },
    async (request, reply) => {

An error crops up upon invoking fastify.authenticate:

Property 'authenticate' does not exist on type 'FastifyInstance<RawServerDefault, IncomingMessage, ServerResponse<IncomingMessage>, FastifyBaseLogger, FastifyTypeProviderDefault>'.ts(2339)

Answer №1

In order to prevent encountering this issue, it is essential to inform the typescript compiler that authenticate is a component of the FastifyInstance interface through the utilization of declaration merging:

declare module "fastify" {
 interface FastifyInstance {
   authenticate: (request: FastifyRequest, reply: FastifyReply) => Promise<void>;
 }
}

If this step is omitted, the typescript compiler will not be able to acknowledge that the authenticate property has been introduced to fastify utilizing decorate.

For further insights, refer to the comprehensive example in the fastify documentation:

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

The identifier 'before' could not be located

While working with jest and typescript, I encountered an issue when using "before" calls: Cannot find name 'before'.ts(2304) I made sure to have @types/jest installed already. Update: It appears that jest does not have a "before" function - it ...

Ways to resolve issues related to null type checking in TypeScript

I am encountering an issue with a property that can be null in my code. Even though I check for the value not being null and being an array before adding a new value to it, the type checker still considers the value as potentially null. Can anyone shed lig ...

How can I suggest the return type of a function that is out of my control?

When I attempt to parse a JSON-formatted string, a linter error is triggered: let mqttMessage = JSON.parse(message.toString()) // ESLint: Unsafe assignment of an `any` value. (@typescript-eslint/no-unsafe-assignment) Given that I am in control of the con ...

Having difficulty converting string columns/data to numerical values when exporting an Ag-Grid table to Excel with getDataAsExcel function

I am having an issue with exporting data from my ag-grid table to excel using the API method getDataAsExcel. The problem arises because I have a column containing only string values, while all other columns are numeric and displayed in the ag-grid table a ...

Combining namespaces in Typescript declaration files

Currently, I am attempting to combine namespaces from d.ts files. For example, when I attempt to merge namespaces in a single file, everything works as expected. declare namespace tst { export interface info { info1: number; } var a: ...

Utilize async/await to send images using node mailer

How can I correctly access mailOptions in the triggerExample.ts file? mail.ts: export const sendNewMail = async (html: string, emails: string[]) => { let smtpTransport = nodemailer.createTransport({ service: "Gmail", auth: { u ...

Issue encountered when working with interface and Observable during the http parsing process

Visual Studio File Structure Error app(folder) -->employee-list(folder) -->employee-list.component.html -->employee-list.component.ts -->app.component.html -->app.component.ts -->app.module.ts -->employee.json ...

Performing addition in Angular 2 with the help of TypeScript

Here is a code snippet of a component I have written: export class AppComponent { public num1: number = 2; public num2: number = 3; public sum: number = 0; public add() { this.sum = this.num1 + this.num2; } } However, when I r ...

Is there a way to convert a JSON input object to a model class using TypeScript in a Node.js application?

Currently, I am developing my Node.js server using TypeScript and the express framework. Here is an example of what my controller and route looks like: export class AuthController { public async signUpNewUser(request: Request, response: Response) { ...

Precise object mapping with Redux and Typescript

In my redux slice, I have defined a MyState interface with the following structure: interface MyState { key1: string, key2: boolean, key3: number, } There is an action named set which has this implementation: set: (state: MyState, action: PayloadAct ...

Struggling to create a TypeScript definition file - the JSX element 'SideMenu' lacks any construct or call signatures

I am currently working on creating a type definition file for react-native-side-menu in order to properly declare it. I have integrated it into a TypeScript project, but unfortunately, there are no TypeScript definitions available. Normally, my approach i ...

The submit button seems to be unresponsive or unreactive

As a newcomer to Angular 2 and Typescript, I am in the process of building a web application. I have created several input fields and, following user submission via a button, I want to log the inputs to the console. However, it seems like my button is not ...

Is it possible to customize the color of the placeholder and clear-icon in the ion-search bar without affecting

I am working with two ion-search bars and I need to customize the placeholder and clear icon color for just one of them. <ion-searchbar class="search-bar" placeholder="search"></ion-searchbar> My goal is to target a specific i ...

I desire for it to effortlessly unlock within my matmenu as soon as the webpage loads

Upon opening my page, I want the material menu to automatically open. However, since there is no click action, I am encountering an error stating that "trigger" is undefined. An error occurred: TypeError: Cannot read properties of undefined (reading &apo ...

Can anyone guide me on implementing map key autocomplete in Java?

Looking to transform this Typescript code into Java. Here's the code snippet: type CompTypes = "Texture" | "Layer" | "Sound"; Map<CompTypes, Component> components; Any suggestions on how to achieve this in Java? ...

Finding the duration of an audio file in a React/Typescript environment

I've been attempting to determine the duration of an audio file. It seems like the audio property is not included in the file by default. The only properties I see are size, name, and type. Is there a way for me to get the duration of the audio file i ...

Is there a way to set the submitted variable to true when the form group is submitted, then revert it to false when the user makes changes to the form?

With just one FormGroup, I ensure that when a user submits the form with errors the 'submitted' variable is set to true, displaying the errors. However, my challenge now is how to reset this variable to false when the user makes any changes after ...

What is the reason behind decorators needing to utilize apply(this) on a function?

I've been delving into the realm of JavaScript and exploring decorator code. One thing I've noticed is that when looking at decorator code like the example below, the input function always applies to 'this' even though it doesn't a ...

Utilizing an array for substituting sections of a string: a guide

I have an array of values like ['123', '456', '789']. What is the best way to iterate over this array and update parts of a string that contain the text :id in sequence (e.g. users/:id/games/:id/server/:id)? Currently, I&apos ...

Guide to setting up a trigger/alert to activate every 5 minutes using Angular

limitExceed(params: any) { params.forEach((data: any) => { if (data.humidity === 100) { this.createNotification('warning', data.sensor, false); } else if (data.humidity >= 67 && data.humidity <= 99.99) { ...