React + Rails路由配置

时间:2016-04-24 20:44:40

标签: ruby-on-rails ruby-on-rails-4 reactjs

我正在尝试使用rails 4构建一个小的todo应用程序并做出反应。没有什么比这更难了,这只是开始学习如何使用rails的反应,但是我对如何编写我的rails控制器有困难。

  • 目前可以访问的两个网址是 “mysite.local” 以显示所有待办事项,以及 “mysite。 local / todos / 1“ 显示具有更多详细信息的特定待办事项。

  • 我有一个 Todos 控制器,用于响应与待办事项相关的AJAX调用。

  • 包含react应用程序的视图不是“Todos”视图,因为我将在futur中添加更多todos,而react应用程序必须处理所有内容。

我想要做的很简单:我希望rails始终使用react应用程序呈现视图,而不管用于访问网站的URL是什么。我的应用程序中的所有控制器(如 Todos 控制器)仅用于检索将通过反应进行操作的JSON数据。

我找到的解决方案是将react应用程序放在应用程序布局中。这样,当有人第一次访问网站时,它将始终存在。因为它在布局中不会再次渲染,所以react应用程序可以完成它的工作。

我的控制器看起来像这样:

class TodosController < ApplicationController

def index
    respond_to do |format|
        format.html
        format.json { Todo.all }
    end
end

def create
    respond_to do |format|
        format.html
        format.json { Todo.create(todo_params) }
    end
end

def show
    respond_to do |format|
        format.html
        format.json { Todo.find(params[:id]) }
    end
end

private
    def todo_params
        params.require(:todo).permit(:content)
    end
end

使用这样的控制器,我可以进行AJAX调用并获得JSON,这是我的控制器将发送的唯一数据,同时我仍然可以到达 “mysite.local / todos / 1“ 和rails除了呈现空视图外什么都不做。

此方法有效,但我不喜欢它,因为控制器为每个动作呈现视图。当有人第一次访问该网站时,将呈现一个空视图。即使视图为空并且它不会在浏览器上显示任何内容,rails仍然必须执行所有渲染视图的过程。我不知道这个过程是否真的有些成本,但我不喜欢我的应用程序做了一些无用的事情。

如果格式化操作是html,有没有办法告诉rails实际上什么都不做? (=不呈现“索引”或“显示”视图?)

或者有更好的方法来做我想做的事吗?

由于

修改

感谢gobluego,我稍微修改了我的应用程序。我创建了一个 Front 控制器来处理客户端部分。然后我将 Todos 控制器移到 api 文件夹中。

现在是我的routes.rb文件:

root "front#index"

namespace :api, constaints: { format: 'json' } do
  resources :todos, only: [:index, :create, :delete, :show]
end

get '*path' => "front#index", via: :all

和我的新 Todos 控制器:

class Api::TodosController < ApplicationController
respond_to :json
before_action :ensure_json_request 

def index
    respond_with Todo.all 
end

def create
    respond_with Todo.create(todo_params)
end

def show
    respond_with Todo.find(params[:id])
end

private
def todo_params
    params.require(:todo).permit(:content)
end

def ensure_json_request  
  return if request.format == :json
  render :nothing => true, :status => 406  
end 
end

这样,任何网址都由 front #index 处理,除了所有api网址,这就是我想要的。例如,如果某人试图在浏览器中访问 mysite.local / api / todos ,则确保不呈现任何内容, before_action 是如果格式不是json,则使用它并且不呈现任何内容。

1 个答案:

答案 0 :(得分:0)

为什么不使用pages #index作为根路径?这样,TodosController仅负责为您的应用程序提供后端服务。

作为一项额外措施,您可以强制执行请求和响应仅采用JSON格式。至于实施,this是一个很好的起点。