Help us understand the problem. What is going on with this article?

RESTfulAPIのFrontWebをReact.jsで構築する準備

More than 5 years have passed since last update.

RESTfulAPIのFrontWebをAngular.jsで書こうかと思ったのですが、FRPパラダイムのReact.jsが面白そうなのでこちらで構築してみます。

環境

  • node.js v0.11.14
  • npm v2.1.11
  • bower v1.3.12
  • gulp v3.8.8
  • Yeoman v1.3.3
  • React.js latest

インストール

nodeとnpmをインストールします。

$ brew install node
$ brew install npm

npmで以下ライブラリをインストールします。

$ npm install -g yo bower gulp generator-react-gulp-browserify

ジェネレート

Yeomanで雛形プロジェクトをジェネレートします。
以下の項目を個別に設定できます。

❯◉ Sass with Compass
 ◉ Bootstrap
 ◉ Modernizr
 ◉ HTML template - Jade
 ◉ CoffeeScript for JavaScript
 ◉ Jest for unit tests
$ mkdir Test
$ cd Test
$ yo react-gulp-browserify

     _-----_
    |       |
    |--(o)--|   .--------------------------.
   `---------´  |    Welcome to Yeoman,    |
    ( _´U`_ )   |   ladies and gentlemen!  |
    /___A___\   '__________________________'
     |  ~  |
   __'.___.'__
 ´   `  |° ´ Y `

You're using the fantastic React generator. We provide you full JavaScript solution with Sass support!
? What is this project's name? Test
❯◉ Sass with Compass
 ◉ Bootstrap
 ◉ Modernizr
 ◉ HTML template - Jade
 ◉ CoffeeScript for JavaScript
 ◉ Jest for unit tests
? What more would you like? Sass with Compass, Bootstrap, Modernizr, HTML template - Jade, CoffeeScript for JavaScript, Jest for unit tests
   create package.json
   create gulpfile.js
   create bower.json
   create app/styles/main.scss
   create app/index.html
   create app/scripts/app.coffee
   create app/scripts/ui/Timer.coffee
   create app/scripts/ui/__tests__/Timer-test.js
   create app/favicon.ico
   create .bowerrc
   create .gitignore
   create app/robots.txt
   create .editorconfig
   create .jshintrc


I'm all done. Running bower install & npm install for you to install the required dependencies. If this fails, try running the command yourself.


npm WARN package.json test@0.0.0 No description
npm WARN package.json test@0.0.0 No repository field.
npm WARN package.json test@0.0.0 No README data
bower not-cached    git://github.com/Modernizr/Modernizr.git#^2.8.3
bower resolve       git://github.com/Modernizr/Modernizr.git#^2.8.3
bower cached        git://github.com/twbs/bootstrap-sass.git#3.3.1
bower validate      3.3.1 against git://github.com/twbs/bootstrap-sass.git#>=3.3.0
bower cached        git://github.com/jquery/jquery.git#2.1.1
bower validate      2.1.1 against git://github.com/jquery/jquery.git#~2.1.1
bower cached        git://github.com/jquery/jquery.git#2.1.1
bower validate      2.1.1 against git://github.com/jquery/jquery.git#>= 1.9.0
bower download      https://github.com/Modernizr/Modernizr/archive/v2.8.3.tar.gz
bower extract       modernizr#^2.8.3 archive.tar.gz
bower invalid-meta  modernizr is missing "main" entry in bower.json
bower invalid-meta  modernizr is missing "ignore" entry in bower.json
bower resolved      git://github.com/Modernizr/Modernizr.git#2.8.3
npm WARN engine jest-cli@0.1.18: wanted: {"node":"0.8.x || 0.10.x"} (current: {"node":"0.11.14","npm":"2.1.11"})

> v8flags@1.0.8 install /Users/susieyy/tmp/yo/node_modules/gulp/node_modules/v8flags
> node fetch.js

bower new           version for git://github.com/jquery/jquery.git#~2.1.1
bower resolve       git://github.com/jquery/jquery.git#~2.1.1
bower new           version for git://github.com/jquery/jquery.git#>= 1.9.0
bower resolve       git://github.com/jquery/jquery.git#>= 1.9.0
bower download      https://github.com/jquery/jquery/archive/2.1.3.tar.gz
bower download      https://github.com/jquery/jquery/archive/2.1.3.tar.gz
bower extract       jquery#~2.1.1 archive.tar.gz
bower extract       jquery#>= 1.9.0 archive.tar.gz
bower resolved      git://github.com/jquery/jquery.git#2.1.3
bower resolved      git://github.com/jquery/jquery.git#2.1.3
bower install       bootstrap-sass-official#3.3.1
bower install       modernizr#2.8.3
bower install       jquery#2.1.3

開発用RESTFulAPIサーバへのProxy設定

/apiというPrefixでパスにアクセスした場合に、localhostの3000ポートにプロキシする設定を行います。
gulpでプロキシを行うために、以下のパッケージをインストールします。

$ npm install --save-dev gulp-connect
$ npm install --save-dev proxy-middleware

続いて以下をgulpfile.jsに追記します。

gulpfile.js
var connect = require('gulp-connect');
var proxy = require('proxy-middleware');
var url = require('url');

gulp.task('connect', function() {
  connect.server({
    root: ['dist'],
    port: 9000,
    livereload: true,
    // /apiにきたリクエストは http://localhost:3000/api にプロキシする。
    middleware: function(connect, o) {
        return [ (function() {
            var options = url.parse('http://localhost:3000/api');
            options.route = '/api';
            return proxy(options);
        })() ];
    }
  });
});

gulp.task('default', ['connect']);

サーバ起動

localhostの9000ポートでアクセスできるようになります。

$ gulp watch

DevSpot_Front.jpg

コード

メインのスクリプトはこんな感じです。
React.jsが宣言的なので、簡素に表記するCoffeeScriptとも相性がよさそうです。

app/scripts/app.coffee
###*
@jsx React.DOM
###
React = window.React = require("react")
Timer = require("./ui/Timer.coffee")
mountNode = document.getElementById("app")
TodoList = React.createClass(
  displayName: "TodoList"
  render: ->
    createItem = (itemText) ->
      React.createElement "li", null, itemText

    React.createElement "ul", null, @props.items.map(createItem)
)
TodoApp = React.createClass(
  displayName: "TodoApp"
  getInitialState: ->
    items: []
    text: ""

  onChange: (e) ->
    @setState text: e.target.value
    return

  handleSubmit: (e) ->
    e.preventDefault()
    nextItems = @state.items.concat([@state.text])
    nextText = ""
    @setState
      items: nextItems
      text: nextText

    return

  render: ->
    React.createElement "div", null, React.createElement(TodoList,
      items: @state.items
    ), React.createElement("form",
      onSubmit: @handleSubmit
    , React.createElement("input",
      onChange: @onChange
      value: @state.text
    ), React.createElement("button", null, "Add #" + (@state.items.length + 1))), React.createElement(Timer, null)
)
React.renderComponent React.createElement(TodoApp, null), mountNode

Javascriptの場合はこんな感じです。

app/scripts/app.js
/** @jsx React.DOM */

var React = window.React = require('react'),
    Timer = require("./ui/Timer"),
    mountNode = document.getElementById("app");

var TodoList = React.createClass({
  render: function() {
    var createItem = function(itemText) {
      return <li>{itemText}</li>;
    };
    return <ul>{this.props.items.map(createItem)}</ul>;
  }
});
var TodoApp = React.createClass({
  getInitialState: function() {
    return {items: [], text: ''};
  },
  onChange: function(e) {
    this.setState({text: e.target.value});
  },
  handleSubmit: function(e) {
    e.preventDefault();
    var nextItems = this.state.items.concat([this.state.text]);
    var nextText = '';
    this.setState({items: nextItems, text: nextText});
  },
  render: function() {
    return (
      <div>
        <h3>TODO</h3>
        <TodoList items={this.state.items} />
        <form onSubmit={this.handleSubmit}>
          <input onChange={this.onChange} value={this.state.text} />
          <button>{'Add #' + (this.state.items.length + 1)}</button>
        </form>
        <Timer />
      </div>
    );
  }
});


React.renderComponent(<TodoApp />, mountNode);

REF

susieyy
フリーランス - スタートアップエンジニアリングアドバイザー - iOS技術顧問 - プロトタイプ開発
https://susieyy.com
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Comments
No comments
Sign up for free and join this conversation.
If you already have a Qiita account
Why do not you register as a user and use Qiita more conveniently?
You need to log in to use this function. Qiita can be used more conveniently after logging in.
You seem to be reading articles frequently this month. Qiita can be used more conveniently after logging in.
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
ユーザーは見つかりませんでした