You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用fastify-jwt签署JWT时遇到Fastify未定义的技术问题

解决Fastify处理函数中'fastify'未定义无法签署JWT的问题

你的问题很典型——因为postJoinHandler是一个独立的函数,它所在的作用域里没有fastify实例的引用,所以直接调用fastify.jwt.sign会报错。下面给你几种可行的解决办法:

方法一:通过request.server访问Fastify实例

Fastify的request对象自带server属性,它指向当前的Fastify实例。你可以直接用这个属性来调用jwt的sign方法,不需要额外传递实例:

修改你的处理函数:

const postJoinHandler = async ( request: any, reply: any ): Promise<{ id: string; name: string }> => {
  try {
    const { username, password } = request.body;
    // 改用request.server获取fastify实例
    const token = request.server.jwt.sign({ username, password });
    return reply.code(201).send(token);
  } catch (error) {
    request.log.error(error);
    return reply.send(400);
  }
};

这个方法最简单,不需要改动其他代码结构,适合快速修复。

方法二:用工厂函数生成处理函数

如果以后需要在处理函数里用到更多Fastify的功能,可以把处理函数改成一个工厂函数,接收fastify实例作为参数,返回真正的处理函数:

第一步:修改处理函数为工厂函数

// handlers/auth.ts
export const createPostJoinHandler = (fastify: any) => {
  return async (request: any, reply: any): Promise<{ id: string; name: string }> => {
    try {
      const { username, password } = request.body;
      const token = fastify.jwt.sign({ username, password });
      return reply.code(201).send(token);
    } catch (error) {
      request.log.error(error);
      return reply.send(400);
    }
  };
};

第二步:在路由注册时传入fastify实例生成handler

// schemas/auth.ts
import { createPostJoinHandler } from '../handlers/auth';

// 改成接受fastify参数的函数,返回schema对象
export const createPostJoinSchema = (fastify: any) => ({
  schema: {
    body: {
      type: 'object',
      required: ['username', 'password', 'email', 'fullname'],
      properties: {
        name: { type: 'string' },
        password: { type: 'string' },
      },
    },
    response: {
      201: {
        type: 'object',
        properties: {
          username: { type: 'string' },
          password: { type: 'string' },
        },
      },
    },
  },
  handler: createPostJoinHandler(fastify),
});

第三步:在路由插件里调用生成函数

// routes/auth.ts
import { FastifyPluginAsync } from 'fastify';
import { createPostJoinSchema } from '../schemas/auth';

const auth: FastifyPluginAsync = async (fastify): Promise<void> => {
  fastify.post('/auth/join', createPostJoinSchema(fastify));
};
export default auth;

这种方式更灵活,适合处理函数需要依赖Fastify实例的多种功能的场景。

方法三:直接在路由插件里定义处理函数(适合简单场景)

如果你的处理逻辑不复杂,也可以直接把处理函数写在路由插件的作用域里,这样天然就能访问到fastify实例:

// routes/auth.ts
import { FastifyPluginAsync } from 'fastify';

const auth: FastifyPluginAsync = async (fastify): Promise<void> => {
  fastify.post('/auth/join', {
    schema: {
      body: {
        type: 'object',
        required: ['username', 'password', 'email', 'fullname'],
        properties: {
          name: { type: 'string' },
          password: { type: 'string' },
        },
      },
      response: {
        201: {
          type: 'object',
          properties: {
            username: { type: 'string' },
            password: { type: 'string' },
          },
        },
      },
    },
    handler: async (request: any, reply: any) => {
      try {
        const { username, password } = request.body;
        const token = fastify.jwt.sign({ username, password });
        return reply.code(201).send(token);
      } catch (error) {
        request.log.error(error);
        return reply.send(400);
      }
    }
  });
};
export default auth;

这种方式省去了文件拆分的麻烦,适合小型项目或者简单的路由处理逻辑。

另外提醒一下:你在postJoinSchema的body定义里,required数组包含了email和fullname,但properties里只有name和password,这里可能有个小错误,建议保持一致哦。

内容的提问来源于stack exchange,提问作者Bill

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.30 18:57:37