はじめに
プロジェクトでNuxt3を採用することになったため、とりあえず開発できるように使いそうな機能等をメモ
理解編は別で投稿するかも
前提
- SSR
- 静的ファイルはAWS S3 + CloudFront, バックエンドはAWS Lambda, DBはRDS(postgresql)
- デプロイはCodeCommit + CodeBuild + AWS CLIでやるので、Serverless Frameworkは使用しない(今後検討するかも)
インストール
npx nuxi@latest init <project-name>
cd <project-name>
npm i
npm run dev # 初期状態で開発サーバー起動
npm run build # ビルド
設定変更
AWS Lambda用に変更
export default defineNuxtConfig({
- devtools: { enabled: true }
+ nitro: {
+ preset: 'aws-lambda'
+ }
})
ディレクトリ構成
/
├─ .output/ -- build時に出力されるファイル
├─ assets/ -- 共通のCSSなどを置く
├─ components/ -- 画面のパーツなどを配置するファイル
├─ layouts/ -- レイアウトを指定する
├─ pages/ -- ページを配置する これがあるとルーティングが有効になる
├─ public/ -- 静的ファイルを配置
├─ server/ -- バックエンドコードを配置
├─ app.vue
├─ buildspec.yml -- CodeBuildでデプロイする際の設定ファイル
└─ nuxt.config.ts
フロント側
app.vue
layout
、pages
ディレクトリを使う場合は以下に変更する
<template>
<div>
- <NuxtWelcome />
+ <NuxtLayout>
+ <NuxtPage />
+ </NuxtLayout>
</div>
</template>
カスタムコンポーネントの双方向バインディング
昔のVue3を少し触ってたことがあり、その頃から変わっていたので戸惑った
昔はv-model
== :value + @input
(※書き方による)だったが、
今はv-model
== :model-value + @update:model-value
Auto-imports
Nuxtでは、よく使いそうなNuxt APIやVue APIは自動でインポートされるので、import文を書かなくて良い
Composition API
NuxtというよりVue側の仕様
<script setup>
と書くといい感じにしてくれる
変数や関数がバインドされ、<template>
内で使用できる
ボイラープレートがめちゃくちゃ減ってHappy
リアクティブ
ref()
で変数に格納する
ref()
はVueの機能で、これもNuxtでauto importされている
<template>
<div>
<button @click="count++">+</button>
{{ count }}
<button @click="count--">-</button>
</div>
<template>
<script setup>
const count = ref(0)
</script>
reactive()
もある(違いは未調査)
ルーティング
Nuxtはファイルベースルーティング
pages以下に配置したファイルがそのままパスになる
ルーティング例
以下のようなディレクトリ構成にすると、
pages
├─ index.vue
├─ help.vue
└─ details/
├─ detail1.vue
└─ detail2.vue
以下のようなルーティングになる
/
/help
/details/detail1
/details/detail2
UIでルーティングする方法は主に2つ
1.NuxtLink
を使う(nuxtっぽい方法)
<template>
<NuxtLink to="/hoge">to hoge</NuxtLink>
</template>
2.navigateTo
を使う(vueっぽい方法)
<template>
<button @click="navigate">プログラムでページ遷移</button>
<button @click="() => navigateTo({path: '/fuga'})">遷移処理だけなら直接書いても良い</button>
</template>
<script setup lang="ts">
const navigate = () => navigateTo({path: '/hoge'});
</script>
NuxtLinkはデフォルトではリンクっぽい見た目になる
ボタンっぽい見た目の遷移UIを作りたいならnavigateToの方が楽かも?
(NuxtLinkをCSSでカスタマイズしてもいいかもしれないが)
ページ遷移時の値の受け渡し
paramsを使いたかったがうまくいかなかった
一旦queryを使う
navigateTo({path: '', query: {id: 1}})
後で調べるメモ:キャッチオールルート、pages/404.vue
バックエンド側
API
/server/api
ディレクトリにhoge.ts
ファイルを置くと、/api/hoge
にルーティングが割り当てられる
そうしたくない場合は、/server/routes
ディレクトリにhoge.ts
ファイルを置くことで/hoge
にルーティングが割り当てられる
tsファイルはdefineEventHandler()
かeventHandler()
をexport default
する必要がある
POSTのbodyを受け取る場合は以下
export default defineEventHandler(async (event) => {
const body = await readBody(event);
console.log(body);
});
API側はダイナミックルーティングには対応していないが、ファイル名に[]
をつけることで変数として受け取ることは可能?
つまり、/server/routes/hoge[id]/fuga.vue
はできないが、/server/routes/hoge/[id].vue
は可能?(要確認)
APIの呼び出し(クライアント側)
<script setup>
直下ではuseFetch
を使う
ボタンクリック時のメソッド内など、レンダリング後に実行されるAPIは$fetch
を使う
(理由はまだ調べてない。メソッド内でuseFetch
を使ったら開発者ツールのコンソールにwarningが出ていた)
AWSにデプロイ後にPOSTメソッドで403になる
CloudFrontのビヘイビアでPOSTも許可する
APIのレスが遅い
デフォルトのLambdaだとメモリが128MBで足りてない
512MBぐらいにすると許容範囲ぐらいになる
上げすぎても意味ない?
DB接続
検証中
その他
biome Prettier / ESLint
biome使いたかったけど、まだvue対応してなかった...orz
Prettier / ESLint使います
linter兼formatter
※npm i
時はbiome
じゃなくて@biomejs/biome
を指定すること
(biome
は別のパッケージ)
npm i --save-dev @biomejs/biome
npx biome init # 設定ファイル生成
設定等はこちらを参照
https://zenn.dev/collabostyle/articles/86477d39be3a2e
同じPCで別プロジェクトもやっておりそちらはESLint/Prettierを使用している
使い分けは、VS Codeでワークスペース単位の設定をし、本プロジェクトではbiomeを使用するように設定
やり方はこちらを参照
https://blog.logical.co.jp/entry/2022/07/25/130000
テスト
nodeは最新バージョンに上げること
古いの(v16.x)を使ってたせいで導入がうまくいかなくて時間を食ってしまった
前は公式が準備中みたいだったが、今はちゃんと書かれているのでこれに従う
その他、未検証事項
今後更新するか、別の記事にしたい
状態管理(未検討)
爆速導入時点では考えなくてもいいかな...?
バリデーション
v-text-field の props に rules を渡すことでバリデーションを実装できる?
zod入れる?
→zod入れる予定
認証
NuxtAuthを使う予定