使用Nuxt3构建强大的API接口:实现前后端数据交互

在 Nuxt 3 中,defineEventHandler 是用于定义服务器端事件处理器的函数,它提供了一个 event 对象,通过这个对象你可以访问请求(request)和响应(response)相关的信息。这个 event 对象包含了许多有用的字段,可以帮助你获取客户端的信息。

常用的 event 字段

  1. event.req: 这是一个 Node.js HTTP 请求对象。它包含了客户端发送的请求信息,如头信息、请求方法等。
  2. event.res: 这是一个 Node.js HTTP 响应对象。你可以通过它来设置响应头、发送响应等。
  3. event.context: 提供了当前请求的上下文信息,如参数、查询字符串等。
// server/api/user.js 
import { defineEventHandler } from 'h3' 
export default defineEventHandler((event) => {  
  // 获取请求方法  
  const method = event.req.method;  
  // 获取请求头  
  const headers = event.req.headers;  
  // 获取查询参数  
  const query = event.context.query;  
  // 获取路由参数  
  const params = event.context.params;  
  // 获取用户代理  
  const userAgent = headers['user-agent'];  
  // 返回一些客户端信息  
  return {  
    method,  
    query,  
    params,  
    userAgent  
    }; 
});
  • event.req.method: 获取 HTTP 请求的方法(如 GET、POST)。
  • event.req.headers: 获取请求的头信息。这可以包括用户代理、接受的内容类型等。
  • event.context.query: 获取 URL 查询参数。例如,对于请求 /api/user?id=123query 将是 { id: '123' }
  • event.context.params: 获取路由参数。这对于动态路由非常有用,例如 /api/user/:id
  • headers['user-agent'] : 从请求头中获取用户代理字符串,这可以告诉你发出请求的浏览器或其他客户端的类型。

每个文件应该导出一个使用defineEventHandler()eventHandler() (别名)定义的默认函数。 处理程序可以直接返回JSON数据、Promise,或使用event.node.res.end() 发送响应。

export default defineEventHandler((event) => {  
  return {  
    hello: 'world' 
  } 
})

页面访问该接口

const { data } = await useFetch('/api/user')

服务器路由

一般将接口写在 server/api/​ 目录下,Nuxt会自动导入,不需要自己显式导入api文件, 直接访问接口 /api/xxx​. 如果要添加没有 /api​前缀开头的api, 可以将接口文件放在/server/routes/​目录中。 例如

-| server/
  ---| api/
  -----| hello.ts      # /api/hello
  ---| routes/
  -----| getUser.ts    # /getUser
useFetch('/api/hello') useFetch('/getUser')

服务器中间件

Nuxt会自动读取**~/server/middleware**目录中的任何文件,以创建项目的服务器中间件。 中间件处理程序将在任何其他服务器路由之前在每个请求上运行,以添加或检查标头、记录请求或扩展事件的请求对象。

export default defineEventHandler((event) => {
  console.log('New request: ' + getRequestURL(event))
})

服务器插件

Nuxt会自动读取 ~/server/plugins目录中的任何文件,并将它们注册为Nitro插件。这允许扩展Nitro的运行时行为并钩入生命周期事件。

export default defineNitroPlugin((nitroApp) => {
  console.log('Nitro plugin', nitroApp) 
})

接口常用使用


匹配HTTP 方法

通过 index.[method].ts​命名方式来以不同的方式组织代码,

server/api/test.get.ts
server/api/test.post.ts 
server/api/test.put.ts 
server/api/test.delete.ts
export default defineEventHandler((event) => {
  // 处理`api/test `端点的POST请求 
})

获取请求体 post

使用 readBody(event)来获取 post请求体

export default defineEventHandler(async (event) => {
  const body = await readBody(event)
  return { body } 
})

调用api,传递 post 参数

<script setup> 
async function submit() {
  const { body } = await $fetch('/api/submit', {
    method: 'post',  
    body: { test: 123 }  
  }) 
} 
</script>

获取查询参数

**/api/query?foo=bar&baz=qux** **通过** getQuery(event)​**获取查询参数**

export default defineEventHandler((event) => {
  const query = getQuery(event)
  return {
   a: query.foo,
   b: query.baz
  }
})

错误处理 自定义返回 code

使用createError​抛出自定义异常,返回指定错误信息

export default defineEventHandler((event) => {
  const id = parseInt(event.context.params.id) as number
  if (!Number.isInteger(id)) {
    throw createError({
      statusCode: 400,
      statusMessage: 'ID should be an integer',
    })  
  }
  return 'All good'
})

指定返回 状态码

通过 setResponseStatus(event, 202)指定返回状态码

export default defineEventHandler((event) => {
  setResponseStatus(event, 202) 
})

运行时配置

Nuxt3 提供了灵活的运行时配置方式,可以在应用运行过程中动态修改配置。 Nuxt3 的运行时配置主要通过 useRuntimeConfig() 方法来实现。useRuntimeConfig() 方法接收一个回调函数,在回调函数中可以通过返回一个对象来指定运行时配置。

第一步:在Nuxt.config.ts中配置 运行时环境和属性

export default defineNuxtConfig({
  runtimeConfig: {
    // 公共运行时配置
    public: {
      baseURL: 'http://localhost:3000'   
    }  
  }  
})

第二步:组件中使用运行时配置

<script setup>
  // 1. 引入 useRuntimeConfig
  const { public } = useRuntimeConfig()
  // 2. 读取运行时配置
  const baseURL = public.baseURL
</script>

第三步:更改运行时配置

<script setup>
  // 1. 获取 nuxtApp 实例  
  const nuxtApp = useNuxtApp()
  // 2. 修改运行时配置
  nuxtApp.$config.public.baseURL = 'http://localhost:8080'
</script>

需要首先获取 nuxtApp​ 实例,然后通过 $config​来更新了运行时配置 public.baseURL​。更新后,App​ 组件读取的运行时配置也会实时更新。

通过 parseCookies(event)​获取 cookie​ 值

export default defineEventHandler((event) => {
  const cookies = parseCookies(event)
  return { cookies } 
})