Express.jsに関しては非常にたくさんの文書が公開されているのでなるべく他の文書とはかぶらないように初めてExpress.jsを使う人が知りたいであろう内容にしぼって基本的なことを中心に説明を行なっています。

動作確認は、MAC環境で行なっており、Node.jsを事前にインストールしておく必要があります。インストール方法は下記を参考に行なってください。

Express.jsのインストール

Express.jsを使って作成するアプリケーションフォルダの作成を行い、そのフォルダに移動します。


 $ mkdir myapp
 $ cd myapp/

Express.jsで使用するパッケージ管理を行うためnpm initコマンドでpackage.jsonファイルの作成を行います。


 $ npm init
npm init -yを実行すると対話モードをスキップしてデフォルト設定でpackage.jsonファイルが作成されます。

npm init実行後、対話モードでいくつか質問をされますが、entry pointではapp.jsを入力してEnterを押してください。それ以外はEnterでかまいません。

本文書ではapp.jsを使うためapp.jsへの変更を行なっていますが変更は必須ではなくindex.jsのデフォルトのままでも問題ありません。


Press ^C at any time to quit.
package name: (myapp) 
version: (1.0.0) 
description: 
entry point: (index.js) app.js
test command: 
git repository: 
keywords: 
author: 
license: (ISC) 

npm initの実行フォルダには、package.jsonファイルが作成されます。

Express.jsのインストールを行う準備が整ったので、npm installコマンドでexpressのインストールを行います。


$ npm install express --save
npm notice created a lockfile as package-lock.json. You should commit this file.
npm WARN myapp@1.0.0 No description
npm WARN myapp@1.0.0 No repository field.

+ express@4.17.1
added 50 packages from 37 contributors and audited 126 packages in 6.607s
found 0 vulnerabilities
npm 5.0+だと–saveをつけなくてもpackage.jsonのdependenciesにパッケージ情報が追加されるので、–saveは必須ではありません。

インストール完了後は、node_modulesフォルダとpackage-lock.jsonファイルが作成されます。ファイル構成は以下のようになります。


$ ls
node_modules		package-lock.json	package.json

Hello Worldをブラウザに表示

Express.jsのインストールが完了したので、Express.jsを使ってブラウザにHello Worldを表示させます。5行のコードでHello Worldを表示させることができます。

myappフォルダにapp.jsファイルを作成して以下のコードを記述します。


const express = require('express')
const app = express()
const port = 3000

app.get('/', (request, response) => request.send('Hello World!'))

app.listen(port, () => console.log(`Example app listening on port ${port}!`))

JavaScriptのアロー関数に慣れていない人もいると思うので、アロー関数を使わない場合の記述も載せておきます。


app.get('/', function(request, response){
       response.send('Hello World!')
}

app.listen(port, function(){
        console.log(`Example app listening on port ${port}!`)
}

上記のコードは3つの部分に分割できるので各部分について説明を行なっていきます。


const express = require('express')
const app = express()

expressモジュールをrequireで読み込んでexpressアプリケーションを作成し変数appに登録しています。このappがexpress.jsのコアになる部分で、appを通してさまざまな設定を行なっていきます。


const port = 3000

app.listen(port, () => console.log(`Example app listening on port ${port}!`))

ブラウザからアクセスするためのポートを3000に設定し、そのポートをリスニングする設定を行なっています。ブラウザからアクセスする際(http://localhost:3000)のポートの設定になります。


app.get('/', (request, response) => response.send('Hello World!'))

上記ではルーティングの設定を行なっています。”/”ルートにアクセスが行われるとresponseのsendメソッドでHello World!を返します。requestはRequest(リクエスト)を表し、postリクエストなどの外側から入ってくるデータを持っています。responseはResponse(レスポンス)を表しており、アクセスしてきたユーザに戻すデータ持っています。getはGETメソッドのことを表しています。

node app.jsコマンドを実行するとExpressサーバが起動します。express.jsの設定でポート3000に設定しているので3000経由でアクセスすることが可能になります。


$ node app.js
Example app listening on port 3000!

3000ポートでサーバが起動しているので、ブラウザでそのポートに対してアクセスを行うと画面にHello Worldが表示されます。

Hello Worldがブラウザに表示
Hello Worldがブラウザに表示

まだ”/”ルートしかルーティングの設定を行なっていないので、それ以外の場所/test等にアクセスを行うとCannot GET /testとエラーが表示されます。/testはアクセスした場所によって変わります。

ポートの3000以外(localhost:4000)を設定するとエラーが表示されアクセスすことはできません。もし異なるポートでアクセスしたい場合は、app.jsのポート番号を別の番号に変更する必要があります。

ルーティングの基本

ルーティングとは

/userという場所をExpress.jsに追加し、ブラウザからGETやPOSTメソッドを使って/userにアクセスがあった場合にどのような処理やレスポンスを返すのかを決めるのがルーティングです。/userという一つの場所であってもメソッド毎に複数のルーティングを設定することができます。

ブラウザからページの閲覧だけを行いたい場合はGETメソッドを使ってページのデータを取得します。POSTメソッドは入力フォームなどでユーザが入力したデータをサーバに渡す際に利用します。

/userにGETメソッド、POSTメソッドの異なる方法でリクエストがあった場合は下記のようにappのgetメソッドとpostメソッドを使い、ブラウザに返す値やサーバで実行する処理を変えることができます。

/userにGETメソッドでリクエストがあった場合


app.get('/user', function (request, response) {
  response.send('Hello World!')
})

/userにPOSTメソッドのリクエストがあった場合


app.post('/user', function (request, response) {
  response.send('Got a POST request')
})

ルーティングを追加

新たに”/”にPOSTメソッドがあった場合のルーティングを追加します。app.getではなくPOSTメソッドの場合はapp.postになります。


app.get('/', (request, response) => response.send('Hello World!'))
app.post('/', (request, response) => response.send('Hello World! by Post Request'))
app.jsファイルの更新を行ってもExpress.jsサーバは自動で更新を反映してくれないため、node app.jsコマンドを停止して更新後node app.jsを実行する必要があります。ファイルの更新を監視するnodemonを後ほどインストールします。

同じ”/”ルートにGETとPOSTの設定を行なっていますが、ブラウザから通常のアクセスを行うとGETメソッドでのアクセスになるので、Hello World!が表示されます。

通常のWEBサイトでは入力フォームから入力した値をサーバに対して送信する際にPOSTメソッドで”/”にアクセスしますが、Express.jsでの入力フォームの作成方法は後ほど確認するので代わりにcurlコマンドを利用します。-XオプションにPOSTを指定することでPOSTメソッドでのアクセスを行うことができます。


$ curl -X POST http://localhost:3000
Hello World! by Post Request

同じ”/”ルートでもルーティングの設定を適切に行えば、GETメソッドとPOSTメソッドで戻される値が変わることが確認できました。

追加でルーティングを増やせばアクセスできる場所も増やすことが可能です。


app.get('/user', (request, response) => response.send('Hello John Doe'))

http://localhost:3000/userにアクセスすれば、Hello John Doeが表示されます。

ファイル更新後は忘れずにnode app.jsコマンドを再実行する必要があります。

nodemonインストール

app.jsのファイルを書き換えるとこれまではnode app.jsを再実行しなければ変更したファイルの内容は反映されませんでした。ファイルの変更を監視し自動でnode app.jsを再実行してくれるnodemonパッケージのインストールを行います。

npm installコマンドでnodemonのインストールを行います。


$ npm install nodemon

インストール後は、下記のコマンドを実行してサーバの起動を行います。


$ npx nodemon app.js
[nodemon] 1.19.1
[nodemon] to restart at any time, enter `rs`
[nodemon] watching: *.*
[nodemon] starting `node app.js`
Example app listening on port 3000!

app.jsファイルの更新があるとnodemonがファイルの更新を検知してnode app.jsコマンドの再実行を自動で行ってくれます。


[nodemon] restarting due to changes...
[nodemon] starting `node app.js`
Example app listening on port 3000!

htmlファイルを表示させたい

ルーティングの設定によりブラウザから/userにアクセスがあると文字列を返すことができました。

htmlタグで文字列を囲むと戻り値を受け取ったブラウザはHTMLタグを解釈してくれるためh1タグをつけると文字は大きく表示されます。


app.get('/user', (request, response) => response.send('<h1>Hello John Doe!</h1>'))
h1タグで文字が大きくなった
h1タグで文字が大きくなった

sendメソッドの中にhtml文書を記述するのは非効率なので、htmlファイルの内容を表示させる方法を確認していきます。

静的ファイルの保存場所の設定

静的ファイルを扱うためには、ミドルウェアのexpress.staticを下記のように設定する必要があります。publicは任意の名前をつけることができます。


app.use(express.static(path.join(__dirname, 'public')))

pathモジュールを利用するため、const path = require(‘path’)が必要になります。


const path = require('path')

__dirnameによりapp.jsファイルが存在するフォルダのパスがわかります。path.joinで結合することでapp.jsファイルが保存されているフォルダの下のpublicフォルダを設定しています。

myappフォルダの中にpublicフォルダを作成してtest.htmlファイルを作成します。


<!DOCTYPE html>
<html lang="ja"></html>
<head>
    <meta charset="UTF-8">
    <title>Express.js</title>
</head>
<body>
    <h1>Hello World</h1>
    <p>Express.jsを使ってtest.htmlファイルを表示しています。</p>
</body>
</html>

ブラウザからhttp://localhost/test.htmlファイルに直接アクセスすると下記の画面が表示されます。express.staticを利用することでpublic以下に保存した静的ファイルに直接アクセスできることがわかります。

test.htmlファイルでHello World
test.htmlファイルでHello World

publicフォルダにimgフォルダを作成し画像を保存します。このファイルにtest.htmlからアクセスできるか確認します。srcのパスはimg/express.pngとしています。


<body>
    <h1>Hello World</h1>
    <p>Express.jsを使ってtest.htmlファイルを表示しています。</p>
    <img src="img/express.png">
</body>

express.staticでpublicを設定しているので、その下のフォルダへはpublic以下のパスを記述するだけでアクセスできることがわかります。

test.htmlから画像を読み込む
test.htmlから画像を読み込む

次にルーティングを利用してhtmlファイルをブラウザに表示させるため、sendFileメソッドを利用します。この場合は、ファイルのパスはpublicからの相対パスではなく絶対パスを設定します。


app.get('/test', (request, response) => response.sendFile(path.join(__dirname, 'public/test.html')))

http://localhost/testにアクセスすると先程と同じ内容が表示されます。

test.htmlから画像を読み込む
test.htmlから画像を読み込む

入力フォームからデータ取得したい

body-parserの利用

htmlファイルの表示方法がわかったので、入力フォームを作成しExpress.js側でデータを取得する方法を確認します。

入力フォームから送られてくるデータを処理するためにbody-parserのインストールを行います。


 $ npm install body-parser

インストール完了後にapp.jsファイルでbody-parserをrequireします。


const bodyParser = require('body-parser');

送られてくるデータのContent-Typeがapplication/x-www-form-urlencodedの場合body-parserのurlencoded()メソッドを利用します。これらの設定により、送られてくるデータはreq.bodyに保存されます。

POSTリクエストを送る場合には2つの方法があり、x-www-form-urlencodedはサーバに対してテキストデータを送る際に使用されます。ファイルを送る場合には、multipart/form-dataが使用されます。

app.use(bodyParser.urlencoded({ extended: true }));
送られてくるContent-Typeを確認したい場合は、response.send(request.header(‘Content-Type’))で確認することができます。

入力フォームの作成

入力フォームは/testにブラウザがアクセスがあった場合に返すtest.htmlファイルの中に記述します。


app.get('/test', (request, response) => response.sendFile(path.join(__dirname, 'public/test.html')))

test.htmlに入力フォームを追加し、送信ボタンを押すと/testに入力したデータをPOSTします。


<h1>入力フォーム</h1>
<form action="/test" method="POST">
    <input type="text" name="name">
    <button type="submit">送信</button>
</form>

入力データの取得

作成したフォームにユーザ名を入力して、送信ボタンを押します。サーバ側のPOSTメソッドに対するルーティングが設定されていないので、Cannot POST /testエラーが表示されます。

入力フォームを作成
入力フォームを作成

サーバ側でルーティングの追加を行います。

送信したデータはbody-parserにより、req.bodyの中に保存されるので、req.body.nameで入力した値を取り出します。受け取ったデータの内容を確認するためにsendメソッドでブラウザに戻します。


app.post('/test', (request, response) => response.send('送信したユーザ名は' + request.body.name))

入力フォームに入れて送信ボタンを押すとExpress.js側でPOSTデータを受け取りbody-parserで受け取ったデータを扱える形に変換して、その結果がブラウザに表示されます。

入力した内容が戻される
入力した内容が戻される

body-parserを利用することでPOSTで送られてきたデータをExpress.jsで取得できることが確認できました。