LoginSignup
4
2

More than 3 years have passed since last update.

FirebaseとNuxt.jsで、CRUDのベストプラクティスを作ってみる。(主にFirebaseまわりについて)

Posted at

FirebaseとNuxt.jsで、CRUDのベストプラクティスを作ってみます。

できあがったもののプレビューはこちらから
■nuxt-basic-crud2
https://nuxt-basic-crud2.firebaseapp.com

作ったファイルは以下にアップしています。
■dog-ears/nuxt-basic-crud
https://github.com/dog-ears/nuxt-basic-crud

【環境】
・Windows10
・Visual Studio Code
・Node(Nodist)

ホスティングは、firebase hostingを使用する。
データベースは、Cloud Firestoreを使用する。

Nuxtは、サーバーサイドレンダリング(SSR)させる。
yarnは使わず、npmを使う。

(1)環境の準備

1) Visual Studio Codeをインストール

2) Nodeは、Nodistを使用。

■Nodist(公式)
https://github.com/nullivex/nodist/releases

2020年2月現在、Cloud FunctionsのNode.jsのバージョンは、10.15.3

■The Node.js 10 Runtime(英語)
https://cloud.google.com/functions/docs/concepts/nodejs-10-runtime?hl=en

nodistインストール後、下記実行

nodist + 10.15.3
nodist 10.15.3

nodeのバージョンは、10.15.3
npmのバージョンは、6.4.1
npxのバージョンは、10.2.0

(2)Firebase の準備およびhostingテストまで。

1) firebaseコンソールでやること

firebaseコンソールをブラウザで開く
https://console.firebase.google.com

googleアカウントでログインする。

プロジェクトの作成
googleアナリティクスは使用するとする。

Databaseを選択し、「データベースの作成」を選ぶ
「テストモードで開始」を選んで、「有効にする」を押す

Hostingを選択し、始めるを選ぶ。

2)Firebase CLIのインストールおよびデプロイまで

ローカルにプロジェクトフォルダを作成する。
以後、[project_folder]とする。

Visual Studio Codeで、プロジェクトフォルダを開きコンソールから、以下実行

CLIのインストール

npm install -g firebase-tools

ログインと初期化

firebase login
firebase init
? Are you ready to proceed?
→ Y

? Which Firebase CLI features do you want to set up for this folder? Press Space to select features, then Enter to confirm your choices. (Press <space> to select)
→ Firestore、Functions、Hosting

? Select a default Firebase project for this directory:
→Use an existing project
→ 先ほど作ったプロジェクトを指定

— Firestore関連の質問 —

? What file should be used for Firestore Rules? (firestore.rules)
→ そのままenter

? What file should be used for Firestore indexes? (firestore.indexes.json)
→ そのままenter

— Functions関連の質問 —

? What language would you like to use to write Cloud Functions?
→ Javascript

? Do you want to use ESLint to catch probable bugs and enforce style? (y/N)
→ n

? Do you want to install dependencies with npm now?
→ Y

— Hosting関連の質問 —

? What do you want to use as your public directory? (public)
→ そのままenter

? Configure as a single-page app (rewrite all urls to /index.html)?
→ N

これで、Firebaseの初期化が完了しました。
ディレクトリ構成は以下のようになっているかと思います。

[プロジェクトディレクトリ]
┣functions
┃┣node_modelus
┃┣.gitignore
┃┣index.js
┃┣package-lock.json
┃┗package.json
┣public
┃┣404.html
┃┗index.html
┣.firebaserc
┣.gitignore
┣firebase.json
┣firestore.indexes.json
┗firestore.rules

firebase serve

で、ローカルサーバーが立ち上がり、
http://localhost:5001
で、functionsのページが、
http://localhost:5000
で、Welcome Firebase Hosting Setup Completeのページが開きます。

ctrl + cでいったんサーバーを終了。

firebase deploy

で、
https://[プロジェクト名].firebaseapp.com/
にページがアップされます。

(3)Functions の準備およびHostingからFunctionsを呼ぶまで。

1) Node10ランタイムの設定

(参考)SSR モードの Nuxt.js を Firebase に Deploy する Tutorial
https://qiita.com/okamuuu/items/c9f2989241af4a1bf588

node10ランタイムを使えるようにします。

/functions/package.json

"engines": {"node": "8"}
↓
"engines": {"node": "10"}

2) FunctionのhelloWorldテスト

/functions/index.js内に、helloWorldがコメントアウトされているので、
こちらを有効化します。
ついでに、function名をhelloWorldからnuxtServerに変えておきます。

/functions/index.js

// exports.helloWorld = functions.https.onRequest((request, response) => {
// response.send("Hello from Firebase!");
// });
↓
exports.nuxtServer = functions.https.onRequest((request, response) => {
response.send("Hello from Firebase!");
});

ローカルサーバーで確認してみる。

firebase serve --only functions:nuxtServer

無事、Hello from Firebase!が表示されました。

3) HostingからFunctionsを呼び出す。

次に、hostingから、functionsを呼ぶようにします。

/firebase.json

"hosting": {
[中略]
  "rewrites": [
    {
      "source": "**/*.*",
      "destination": "/404.html"
    },
    {
      "source": "**",
      "function": "nuxtServer"
    }
  ]
}
}

※rewritesの上の行の]の後に、「,」を足すのを忘れずに。

拡張子付きのアドレスにアクセスした場合、ファイルがあれば表示。
なければ、notFoundページを表示するようにしました。
それ以外のアドレスは、すべてnuxtServerファンクションを呼ぶようにしてます。

ローカルテスト

firebase serve --only functions:nuxtServer,hosting

http://localhost:5000/hoge
などを開くと、helloWorldが実行されます。
※ただし、ルートに関しては、/public/index.htmlがあるため、そちらの表示が優先されます。

確認後、/publicフォルダの中にあるindex.htmlファイルは、不要なので、削除します。

(4)functions下にnuxtをインストールする

functions下にnuxtをcliでインストールしようと思います。
ただ、普通にfunctionsフォルダで、

npx create-nuxt-app

を実行すると、package.json等が上書きされてしまうので、
いったん下の階層(nuxt-src)にインストールします。

Visual Studio Codeのターミナルで、下記実行

cd functions
npx create-nuxt-app nuxt-src
? Project name
→ なんでもOK

? Project description
→ なんでもOK

? Author name
→ なんでもOK

? Choose a package manager
→ Npm

? Use a custom UI framework (Use arrow keys)
→ Buefy

? Use a custom server framework (Use arrow keys)
→ none

? Choose Nuxt.js modules (Press <space> to select, <a> to toggle all, <i> to invert selection)
→DotEnvのみ選択

? Choose linting tools (Press <space> to select, <a> to toggle all, <i> to invert selection)
→ ESLint、Prettierを選択

? Use a custom test framework (Use arrow keys)
→ none

? Choose rendering mode (Use arrow keys)
→ Universal

? Choose development tools
→ jsconfig.json

インストール完了後、

cd ./nuxt-src
npm run dev

を実行すると、.nuxtフォルダが生成され、
ローカルサーバーが立ち上がり

で、テストページを確認できました。

ローカルサーバーは、ctrl+cでいったん停止しておきます。
/functions/nuxt-src/.nuxtフォルダもいったん削除。

次にnuxtのルートフォルダを一つ上のfunctionsに移動します。

functions/nuxt-src/package.jsonから
functions/package.jsonに、下記のように表記を移動します。

■scripts
→ そのまま全部追加。

startのみ、ダブるのでもともとあったfunctionsのstartは削除します。

"start": "npm run shell", // → こちらを削除
"start": "nuxt start",

ついでに、npm run serveとnpm run deployで、hostingもサーブ・デプロイするように変更しておきます。

"serve": "firebase serve --only functions",
"deploy": "firebase deploy --only functions",
↓
"serve": "firebase serve --only functions,hosting",
"deploy": "firebase deploy --only functions,hosting",

■dependencies、devDependencies
→ まるごと移動でOK

移動が完了したら、
functions/nuxt-src/内の
・node_modules
・package.json
・package-lock.json
・.git ※あれば
は削除します。

nuxt-srcに残ったファイル(※フォルダはそのまま)を上の階層に移動
.editorconfig
.env
.eslintrc.js
.gitignore(※上書きでOK)
.prettierrc
jsconfig.json
nuxt.config.js
README.md

移動したnuxt.config.jsに、以下追加。

srcDir: 'nuxt-src'
build: {
/*
** You can extend webpack config here
*/
extend(config, ctx) {}
},
↓
build: {
/*
** You can extend webpack config here
*/
extend(config, ctx) {},
publicPath: '/assets/'
},

上記すべて終わったら、functionsフォルダで

npm install

を実行しておく。

npm run devすると、
WARN No .env file found in …
が出るので、.env関連を修正する。

nuxt用の.envモジュール「@nuxtjs/dotenv」
公式を見ると、
modulesではなく、buildModulesに入れろと書いてあったので、
buildModdulesに移動しつつ、オプションでパスの指定をします。

buildModules: [
....(中略)
// Doc: https://github.com/nuxt-community/dotenv-module
['@nuxtjs/dotenv', { path: __dirname }]
],

(5)ESlintがらみの設定変更

nuxtをインストールした時点で、
基本的なルールは設定されており、

npm run lint

で、lintチェックを実行できます。

実際に、lintチェックを実行したところ、
\functions\index.js
で、エラーが3つほど出ました。

修正をするにあたり、
まず、functions下に移動した.eslintrc.jsと.prettierrcを
VisualStudioCodeで使えるようにします。

※拡張機能のESLint、Prettierはインストールしておく。

■VisualStudioCodeでESLint拡張機能が動かない気がする時に確認したこと
https://note.kiriukun.com/entry/20190817-eslint-not-working-in-vscode

設定 – eslint.workingDirectories
をワークスペースで定義する。

settings.json
"eslint.workingDirectories": [
  "./functions"
]

これでfunctions/index.htmlを開くと、
エラー箇所に赤波線が表示されます。
赤波線にカーソルを合わせて、「クイックフィックス」→fix this pretier/pretier problem
で、自動的に修正されます。

次に、基本ルールですが、
初期設定でconsole.logが使用禁止のため、
このルールを修正します。

functions/.eslintrc.js

rules: {
'no-console': 'off',

上記のルールで、console出力があってもエラー表示をしなくなります。

(6)function「nuxtServer」で、nuxtをよびだしレンダリングする。

/functions/index.js
を、下記のように変更

コンフィグ内、@nuxtjs/eslint-moduleは残していると、デプロイ後に
Error: could not handle the request
が、発生する。
(ログを見ると、FATAL Cannot find module ‘@nuxtjs/eslint-module’と表示される)
なので、コンフィグを読み込んだ後に、@nuxtjs/eslint-moduleを除外する。

また、index.jsでrequireを使ってnuxt.config.jsを読み込むため、
nuxt.config.jsを以下のように修正します。

export default {
↓
module.exports = {

この時点で、npm run lint で、チェックすると、

1:1 error Unexpected module.exports, please use export default instead nuxt/no-cjs-in-config

が、出る。

CommonJSのrequireを使うなというエラー。
ルールから除外する。

/functions/.eslintrc.js
のrulesに、下記追加

'nuxt/no-cjs-in-config': 'off',

エラーが出なくなった。

nuxtをビルドする

npm run build

ローカルでfirebase サーバーを確認してみる

npm run serve

デプロイしてみる

npm run deploy

→見える(ただしエラーあり。)
/assetsにクライアントスクリプトを探しに行ってしまうので、
.nuxt/dist/clientの中身を/public/assetsにコピー。
これで、エラーが出なくなります。

npm buildしたときに自動的に.nuxt/dist/clientのなかみを
/public/assetsにコピーするようにする

npm install --save-dev cpx rimraf

下記ファイルを修正

/functions/package.json

"scripts": {
  "postbuild": "npm run remove-assets && npm run copy-assets",
  "remove-assets": "rimraf ../public/assets",
  "copy-assets": "cpx ./.nuxt/dist/client/** ../public/assets",

これで npm run buildを実行すると、
/public/assets
内が、自動的に更新される。

/public/assetsは、git対象外にするので、.gitignoreに
public/assets
を追加します。

(7)nuxtを修正する。

必要パッケージを入れる

npm install dayjs firebase htmlspecialchars vuexfire

.envの設定

デフォルトの設定では、サーバーサイドでしか読み取れない。
下記の対応をすることで、クライアントサイドでも読み取れるようになる。

/functions/nuxt.config.js
先頭に以下追加

require('dotenv').config()

Nuxtの修正内容は、以下のコミット履歴から確認できます。

だいぶ投稿が長くなってしまったので、Nuxtの詳細については割愛します。

リポジトリをクローンして、.env.sampleから.envファイルを作って、
npm run devすれば、コンソールで処理の流れが終えるようにしているので、
見ていただければと思います。

4
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
2