Isomorphic React app with Ruby on Rails
Chúng ta sẽ xây dựng một blog tương đối đơn giản.Phần đầu tiên chúng ta chúng ta sẽ cùng nhau setup create view cho list các posts với React components và server-side-rendering.Trong phần thứ 2 chúng ta sẽ move nhiều nội dung vào trong React component add routing, và add các view khác để show ...
Chúng ta sẽ xây dựng một blog tương đối đơn giản.Phần đầu tiên chúng ta chúng ta sẽ cùng nhau setup create view cho list các posts với React components và server-side-rendering.Trong phần thứ 2 chúng ta sẽ move nhiều nội dung vào trong React component add routing, và add các view khác để show detail một post. Trước tiên chúng ta sẽ create một Rails app:
rails new isomorphic-reactjs
Chúng ta cần tới một Javascript enviroment để thực hiện việc việc server-side-rendering của React components. Rails mặc định sử dụng ExecJS. therubyracer gem được include trong một số Rails Gemfile để sử dụng với ExecJS.Chúng ta nên cài đặt NodeJS trên system và ExecJS sử dụng nó trực tiếp.Chắc chắn rằng therubyracer được commented out hoặc removed khỏi Gemfile.
Bây giờ chúng ta có thể tích hợp React vào Rails app của chúng ta.
Đầu tiên là add gem vào Gemfile để sử dụng React:
gem 'react-rails', '~> 1.5.0'
react-rails gem cung cấp:
- React Javascript file(s).
- “Compilation” của JSX files trong Rails assets pipeline.
- Một unobtrusive JavaScript (react_ujs) có thể được tự động mount React components từ DOM elements với specific data-attributes, đáp ứng đầu đủ yêu cầu rằng ứng dụng Javascript sẽ có thể khởi tạo trạng thái của nó từ HTML trên server.
- Một view helper để generate DOM elements compliant đúng với sự kì vọng, khiến nó trở nên dễ dàng có thể đặt React component directly trong view.Helper này chấp nhận một prerender option, với mỗi trigger server-side sẽ rendering components sử dụng nó.
Trong bước tiếp theo:
bundle install
Mọi chuyện ổn phải không nào?
React-rails gem cung cấp một generator để set tất cả những thứ đó trong app.Vì thế khi bạn run:
rails g react:install
.. và kết quả là:
- react và react_ujs được add vào trong file application.js của chúng ta.
- Một thư mục components được create trong app/assets/javascript; đó là nơi chúng ta tổ chức React components.
- File components.js được add vào Javascript asssets.react-rails sẽ load components của chúng ta.
Gem cung cấp 2 biến thể của Javascript library: một phiên bản minified cho production, và unminified cho việc debugging dễ dàng hơn.Chúng ta phải nói với React các biến thể tùy theo môi trường của chúng ta.
Add thêm config sau vào file: config/environments/development.rb:
#React development variant (unminified) config.react.variant = :development
Trong file config: config/environments/production.rb:
#React production variant (minified) config.react.variant = :production
Và bây giờ app của chúng ta đã sẵn sàng để render và serve React components.js
Chúng ta cần một số lượng data mẫu để display trong components đầu tiên vì thế chúng ta sẽ create một model
Blog của chúng ta khá đơn giản.Chúng ta sẽ hiển thị một list các post, mỗi post bao gồm các thông tin:
- title
- author
- text content
- created date
Chúng ta sẽ create model:
rails g resource Post title:string author:string contents:text
Sử dụng db/seeds.rb để create một vài blog:
p = Post.new(title: 'My first post!', author: 'Olivier Lance') p.contents = <<EOF Lorem ipsum dolor sit amet, consectetur adipiscing elit p.save p = Post.new(title: 'Guest post', author: 'John Doe') p.contents = <<EOF Lorem ipsum dolor sit amet, consectetur adipiscing elit EOF p.save p = Post.new(title: 'Closing my blog... :(', author: 'Olivier Lance') p.contents = <<EOF Lorem ipsum dolor sit amet, consectetur adipiscing elit. EOF p.save
Migrate database và seed:
rake db:migrate rake db:seed
Bây giờ chúng ta sẽ customize file được created cho chúng ta.Trước hết là resource được added bởi config/routes.rb.Chúng ta chỉ cần index route cho lúc này, và chúng ta sẽ sửa lại như sau:
resources :posts, only: :index root to: 'posts#index'
Thêm index action trong app/controllers/posts_controller.rb:
class PostsController < ApplicationController def index #Fetch all posts @posts = Post.all end end
Cuối cùng create app/views/posts/index.html.erb view file và sẽ tạo view trong đây.
Chúng ta đã có cơ sở cho ứng dụng React, trước khi tạo component có một vấn đề quan trọng nữa là hiểu chúng ta sẽ nên sử dụng như thế nào? Các thành phần trong React có thể tách các thành phần thực thi mà chúng ta quan tâm.Một React app là một phân cấp của các thành phần chia nhỏ ứng dụng thành các thành phần nhỏ hơn đại diện cho các trạng thái dữ liệu của bạn tại bất kì thời điểm nào.Đó là một khái niệm mạnh mẽ vì một điều là sự không chính xác của các thành phần đó: một thành phần được tạo ra với cùng một dữ liệu lặp đi lặp lại sẽ luôn giống nhau. Làm như vậy, ứng dụng của chúng ta không bao giờ có thể bị fail, vởi vì chúng ta chỉ mô tả nó như thế nào cho mỗi trạng thái có thể của dữ liệu view ra cho người dùng.Vì vậy, nếu đã đảm bảo rằng dũ liệu của chúng ta vẫn nhất quán thì ứng dụng sẽ chạy như ta kì vọng.Đây là những điểm được thiết kế cho kiến trức Flux
Ok, sau đây chúng ta sẽ beak app của chúng ta thành các thành phần, màu sắc ngăn cách các thành phần như dưới đây:
Đó là mục tiêu của chúng ta.Để dễ tiếp cận hơn chúng ta sẽ tập trung vào mục tiêu chính để hiển thị các thành phần trên server.
Các thành phần này là các container cho các bài posts, với Rails, chúng ta thường sử dụng thẻ div với mỗi bài đăng và đặt các class hoặc sử dụng một collection của partials. Đó chính là những gì chúng ta đang làm ở đây, chỉ nó ở trong thành phần React thay vì ERB view Create app/assets/javascripts/components/posts_list.js.jsx và copy đoạn code sau:
var PostsList = React.createClass({ getInitialState: function() { return { posts: this.props.initialPosts }; }, render: function() { var posts = this.state.posts.map(function(post) { return <Post key={post.id} post={post} />; }); return ( <div className="posts"> {posts} </div> ); } });
Tham khảo: https://medium.com/technically-speaking/isomorphic-reactjs-app-with-ruby-on-rails-part-1-server-side-rendering-8438bbb1ea1c