# [Nuxt] Nuxt 3 - Server
###### tags: `Nuxt`
* 支援 HMR 的 API 和 server handlers:`server/api`、`server/routes`、`server/middleware`
* 每個檔案都要 export `defineEventHandler()` 或 `eventHandler()`(別名)
* 可以直接 return JSON 資料、`Promise` 或使用 `event.node.res.end()`
## `server/api`
* 有前綴 `/api`
* 範例:`server/api/user.js` 的路徑為 `/api/user`
* 檔名可以加上 `get` / `post` / `delete` / `put` 等等匹配 HTTP Method
* 範例:`user.get.js`、`user.post.js`
* 若以沒寫到的 Method 發送請求會顯示 405 Method Not Allowed
* 動態參數:檔名以 `[]` 包住參數名稱
```javascript
// server/api/user/[name].js
export default defineEventHandler((event) => {
const name = getRouterParam(event, 'name');
// ...
return {
// ...
};
});
```
## `server/routes`
* 用途和 `server/api` 一樣,但無前綴
* 範例:`server/routes/user.js` 的路徑為 `/user`
* 若檔名和 `pages/` 內的檔案相同,在點擊 `NuxtLink` 的連結會顯示 `pages/` 內同檔名的頁面,在網址列直接輸入網址則會顯示 `server/routes/` 內同檔名的 return 內容
## `server/middleware`
* 攔截 `server/` 所有 Request
* 不應回傳任何內容,也不能中斷或回應請求,只能檢查或增加 `request context` 或拋出錯誤
## `server/plugins`
* 會自動註冊為 Nitro plugins
## `server/utils`
* 可以添加更多 helper
## Server Types
:::warning
Nuxt 版本 >= 3.5
:::
## 使用範例
### 取得 Request 的 Query Parameters
使用 `getQuery(event: H3Event)`
```javascript
<script setup>
const { data } = await useFetch('/api/user', { query: { id: route.params.id } });
</script>
```
```javascript
export default defineEventHandler((event) => {
const query = getQuery(event);
const id = query.id;
// ...
return {
// ...
};
});
```
### 取得 Request 的 Body
使用 `readBody(event: H3Event)`
```javascript
<script setup>
const { data } = await useFetch('/api/user', {
method: 'post',
body: {
id: '1234',
name: 'Ann',
},
});
</script>
```
```javascript
export default defineEventHandler(async (event) => {
const body = await readBody(event);
console.log(body); // { id: '1234', name: 'Ann' }
return {
// ...
};
});
```
:::warning
若在 Get Request 使用 `readBody` 會拋錯 405 Method Not Allowed
:::
### 處理錯誤
* 若沒錯誤,會返回 status code 200
* 任何未捕獲的錯誤會返回 status code 500
* 要返回其他錯誤代碼,使用 `createError`
```typescript
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';
});
```
### 返回其他 status codes
:::info
* [Returning other status codes](https://nuxt.com/docs/guide/directory-structure/server#returning-other-status-codes "server/ · Nuxt Directory Structure")
* [setResponseStatus](https://nuxt.com/docs/api/utils/set-response-status "setResponseStatus · Nuxt Utils")
:::
* 使用 `setResponseStatus(event: H3Event, code?: number | undefined, text?: string | undefined)`
* 只能在 setup functions、plugins 和 route middleware 內調用
```javascript
export default defineEventHandler((event) => {
setResponseStatus(event, 202);
});
```
```javascript
const event = useRequestEvent();
setResponseStatus(event, 404, 'Page Not Found');
```
### 取得 Runtime Config
使用 `useRuntimeConfig(event?: H3Event | undefined)`
### 取得 Request Cookies
使用 `parseCookies(event: H3Event)`
## 參考資料
* [官方文件](https://nuxt.com/docs/guide/directory-structure/server "server/ · Nuxt Directory Structure")
---
:::info
建立日期:2023-08-31
更新日期:2023-09-01
:::