React は JavaScrit による フロントエンド の View ライブラリです。
React tutorialをあえてスクリプトを使わないでアプリケーションを作ります。
JavaScrit のない世界から React への パラダイムシフト を体感してみましょう。
Learning
- React tutorial に Express を利用する。
- View に React (Virtual) DOM ではないテクノロジーを利用する。
Environment
- node: v4.4.5
- npm: v3.9.6
Comment Box Form
- 完成される Source Code のファイルリストです。
$ tree -a -I node_modules
.
├── app.js
├── bin
│ └── www
├── db
│ └── comments.json
├── package.json
├── public
│ ├── images
│ ├── javascripts
│ └── stylesheets
│ └── style.css
├── routes
│ ├── comments.js
│ └── index.js
└── views
├── error.ejs
└── index.ejs
Let's hands-on
Initial application
- Express application generator で Webアプリケーション を作成します。
$ npm install express-generator -g
$ express --ejs express-comment-box-example
$ cd express-comment-box-example && npm install
Add package
- Markdown parser は remarkable を使います。
$ npm install remarkable --save
Add Database
- JSON形式の フラットファイルデータベース でデータを永続化します。
db/comments.json
[
{"id": 1, "author": "Pete Hunt", "text": "This is one comment"},
{"id": 2, "author": "Jordan Walke", "text": "This is *another* comment"}
]
Replace stylesheet
- Stylesheet は React Tutorial からダウンロードします。
$ curl https://raw.githubusercontent.com/reactjs/react-tutorial/master/public/css/base.css \
-o ./public/stylesheets/style.css
Add View
-
EJS の テンプレートエンジン でHTMLの要素を設定します。
- このHTMLに
<script>
の要素はありません!
- このHTMLに
views/index.ejs
<!DOCTYPE html>
<html>
<head>
<title><%= title %></title>
<link rel='stylesheet' href='/stylesheets/style.css' />
</head>
<body>
<div className="commentBox">
<h1>Comments</h1>
<div className="commentList">
<% comments.forEach(function(comment){ %>
<div className="comment">
<h2 className="commentAuthor">
<%= comment.author %>
</h2>
<%- comment.text -%>
</div>
<% }) %>
</div>
<form className="commentForm" action="/" method="post">
<input type="text" placeholder="Your name" name="author" />
<input type="text" placeholder="Say something..." name="text" />
<input type="submit" value="Post" />
</form>
</div>
</body>
</html>
Add Route
- データを フラットファイルデータベース から読み込んでレンダリングする
router.get
を設定します。 - データを フラットファイルデータベース に読み書きしてレンダリングする
router.post
を設定します。
routes/index.js
var express = require('express');
var router = express.Router();
var fs = require('fs');
var Remarkable = require('remarkable');
var md = new Remarkable();
/* GET home page. */
router.get('/', function(req, res, next) {
fs.readFile('db/comments.json', function(err, data) {
var comments = JSON.parse(data);
comments = comments.map(function(comment, index, array) {
return {author: comment.author, text: md.render(comment.text)};
});
res.render('index', {title: 'Comment Box Example', comments: comments});
});
});
/* POST home page. */
router.post('/', function(req, res) {
fs.readFile('db/comments.json', function(err, data) {
var comments = JSON.parse(data);
req.body.id = Date.now();
comments.push(req.body);
fs.writeFile('db/comments.json', JSON.stringify(comments, null, 4), function(err) {
comments = comments.map(function(comment, index, array) {
return {author: comment.author, text: md.render(comment.text)};
});
res.render('index', {title: 'Comment Box Example', comments: comments});
});
});
});
module.exports = router;
Start HTTP Server
-
npm start
コマンドで Webアプリケーション を実行します。 - ブラウザで http://localhost:3000 をロードすると Comment Box Example が表示されます。
$ npm start
$ open http://localhost:3000
Comment Box API
React tutorial で利用する API も作りましょう。
Replace Route
-
routes/index.js
をJSON形式のレスポンスにするだけです。 - CORS(Cross-Origin Resource Sharing)の設定もします。
$ mv ./routes/users.js ./routes/comments.js
routes/comments.js
var express = require('express');
var router = express.Router();
var fs = require('fs');
/* GET comments listing. */
router.get('/', function(req, res, next) {
fs.readFile('db/comments.json', function(err, data) {
res.setHeader('Access-Control-Allow-Origin', '*');
res.json(JSON.parse(data));
});
});
/* POST comment creating. */
router.post('/', function(req, res) {
fs.readFile('db/comments.json', function(err, data) {
var comments = JSON.parse(data);
comments.push(req.body);
fs.writeFile('db/comments.json', JSON.stringify(comments, null, 4), function(err) {
res.setHeader('Access-Control-Allow-Origin', '*');
res.json(comments);
});
});
});
module.exports = router;
Replace Config
-
comments
のモジュールの設定をします。
app.js
var routes = require('./routes/index');
-var users = require('./routes/users');
+var comments = require('./routes/comments');
app.use('/', routes);
-app.use('/users', users);
+app.use('/api/comments', comments);
API Testing
-
curl
コマンドで取得できるか確認します。
$ curl http://localhost:3000/api/comments
[{"id":1,"author":"Pete Hunt","text":"This is one comment"},{"id":2,"author":"Jordan Walke","text":"This is *another* comment"}]
-
curl
コマンドで追加できるか確認します。
$ curl http://localhost:3000/api/comments \
--header 'Content-Type:application/json' \
--data '{"author":"foo","text":"*bar*"}'
[{"id":1,"author":"Pete Hunt","text":"This is one comment"},{"id":2,"author":"Jordan Walke","text":"This is *another* comment"},{"author":"foo","text":"*bar*"}]
Congrats!
1つのViewに CommentBox, CommentList, Comment, CommentForm が集まっているので構成を部品に分離したいです。
次は React tutorial を Hot Module Replacement で進めましょう!