【Reat × Rails(api)、フロントとバックエンドを分けるとはどういう事か理解する】


実務未経験の自分が、
現在、Rails(api)とReact.jsでポートフォリオを作成中ですが、
このようなフロントエンドとバックエンドを分けて開発する事の概念的な部分に関して、
イメージがしづらかったので、アウトプットとして整理しておきます。

※めちゃくちゃ初心者向けの内容になるかと思います。

そもそもフロントエンドとバックエンドを分けるってどういう事??

凄く簡単に言うと、Railsにおけるviewに当たる部分を、別のフレームワークを使って開発すると理解しています。

Railsでアプリを何個か作成していた為、いわゆるviewにあたるファイルが、〇〇.erbという形式で作成しておりました。
しかし、Rails apiモードではviewというディレクトリはありませんし、.erbというファイルも作成しません。
※正確にはviewディレクトリはありますが、ここでuserとかpostだったりのディレクトリは作成しません。

一般的には、このviewというディレクトリの代わりに、front又はfrontendというディレクトリでReactやVueを使って作成していきます。
※viewの代わりにという言い方は語弊あるかもしれませんが、このような理解で良いかと思います。

viewの部分を置き換えるって何??

当たり前ですが、viewの部分が担っていた役割を、そのままReactやVueが行っていく事になります。

何が変わるのかというと、
基本的にページ遷移した際の画面をリロードする必要が無くなり、
ユーザー(クライアント)側の使い勝手が良くなります。
※この辺はこちらの記事を読むと良いです。
今さら聞けない!シングルページアプリケーションとは

ディレクトリ構造的には、こんな感じになります。


※frontendのディレクトリ構造は、ReactやVueのチュートリアルや記事を見て下さい。

Railsにおけるviewの主な役割って何だったっけ?

  • ブラウザ画面の描画
  • 何らかのリクエストを投げて、返ってきた値を受け取る

例えば、下記のような記述があった場合

view/user/show.html.erb
<p>名前</p>
<%= @user.name %>
config/routes.rb
resources :users, only[:show]
controllers/users_controller.rb
@user = User.find(params[:id])

まず、

  • show.html/erbから@userの情報を下さい!というリクエストをresources :user, only[:show]というルーティング宛に送ります。

※どのルーティングが判別するかはRailsが判断してくれています。

次に、

  • routes.rbuser/show.html.erbから来たリクエストは、どのコントローラーのどのアクションに渡すべきか判別します。

最後に

  • controllers/users_controller.rbが受け取ったリクエストを元にUserモデルから該当userを探して、レスポンスを返す

という流れになっているかと思います。

フロントエンドとバックエンドを分けての開発の場合は、
このview/user/show.html.erb@userの情報を下さい!というリクエストを投げる行為を、ReactやらVueやらで行っていきます。

ちなみに、このリクエストを投げる行為の事をapiを叩くと言ったりしています。
※今回の例はGETリクエストですが。

フロントを分けるとどういう動きになるの??

実際の記述は下記のようになります。
かなり省略して書いておりますが、流れを掴めれば良いと思っているので、ご容赦下さい。

UserShow.jsx
get(lokalhost3000/users/:id)

...

return(
  {user.name}
)

※jsxとはReact.jsのファイル端子ですが、Railsでいうviewにあたる部分と思って下さい。

routes.rb
resources :users, only[:show]
users_controller.rb
  def show
    @user = User.find(params[:id])
    render json: { user: @user }
  end

流れの簡単な説明

ルーティングを指定してGETリクエストを投げる

まず、フロントエンドのviewからRailsに向けてuserの情報を下さいとgetリクエストを投げています。
※jsxの記述はかなりハショッております。

Railsでは、@user.nameと記述すれば勝手にRailsがリクエストを投げて値を返すところまで、やってくれていましたが、
フロントを分ける場合は、このようにリクエストを投げる処理を自分で実装しなければなりません。
localhost3000/users/:idrails routesに記載されているルーティングの事です。

また、Railsでよく使っていた、user_pathのようなルーティング指定も使いません。
※使う方法もあるのかもしれませんが、自分は知りません。。

ルーティングが実行すべきコントローラーを判断する

ここはRails単体の動きとなんら変わらないので、パスします。

コントローラーがリクエストを受け取って値を返す

見慣れない書き方が、render json: { user: @user }こちらかと思います。

Rails単体の場合は、@user = User.find(params[:id])だけでも良いのですが、
フロントを分ける場合は、この@userの値をjson形式というデータ形式に変えて渡す必要があります。

jsonとは、簡単に言うとJavascriptのデータ形式と思って頂ければ良いかなと。
詳しく知りたい方は下記を参照下さい。
https://products.sint.co.jp/topsic/blog/json

なぜ、こんな形式に変換しないといけない?

変換をしないままでは、rubyのデータ形式のままでReactやVueはJavaScriptで書くので、
rubyのデータ形式では対応出来ないからです。

Rails単体の場合は、.erbもrubyを元に作成される為、そのままでも対応出来るという事です。

最後に

自分用のアウトプットとはいえ、かなり煩雑に書いてしまったので、
指摘や分かりづらい点があれば、どんどんご指摘下さい。