组织同一模型的两个不同视图的正确方法是什么?

时间:2015-01-31 05:12:08

标签: ruby-on-rails

ROR新手。我已经阅读了很多,但我认为我的吸收速度很慢。我尝试使用相同内容的两个不同视图创建一个Web应用程序:

  1. 一个充满艺术品的页面,供访问者按图像浏览(位于网站的根目录)。
  2. 一个页面,其中列出了相同的艺术作品,并显示了我为他们定义的所有相关属性(媒体等),因此我可以查看与每个艺术作品相关的数据。这应该是我的超级轻量级​​管理页面。
  3. 我的问题是:

    1. 由于我是从脚手架生成这个网站,我现在使用views / artwork / index.html.erb作为管理表视图(应该是私有的),我创建了一个' home&# 39;页面并将一些代码添加到' home' view(和pages_controller)使艺术品出现在那里(面向公众)。 我这样做了吗?这是一种很好的组织方法吗?
    2. 我已经安装了设计并成功隐藏了用于在登录后面的页面上编辑艺术品的链接,但我不知道封锁应用程序部分的正确方法(例如管理表页面,编辑来自世界其他地方的页面等。我应该将这些页面放在不同的文件夹中吗? 如何将这些网页设为私有?
    3. 以下是一些代码段: home.html.erb

      <div id="artworks" class="transitions-enabled">
          <% @artworks.each do |artwork| %>
              <div class="box">
                      <%= link_to image_tag(artwork.image.url(:medium)), artwork %>
              </div>
          <% end %>
      </div>
      

      艺术品/ index.html.erb:

        <div class="row">
          <div class="col-xs-6 col-sm-8 col-md-4">
            <h1>Listing artworks</h1>
          </div>
          <div class="col-xs-4 col-sm-2 col-md-2 col-md-offset-6">
            <%= link_to 'New Artwork', new_artwork_path, class:"btn btn-default" %>
          </div>
        </div>
      
        <div class="table-responsive">
          <table class="table table-striped">
            <thead>
              <tr>
                <th>Image</th>
                <th>Title</th>
                <th>Genre</th>
                <th>Category</th>
                <th>Medium</th>
                <th>Date</th>
                <th>Dimensions</th>
                <th>Availability</th>
                <th>Rating</th>
                <th>Edit</th>
              </tr>
            </thead>
      
            <tbody>
              <% @artworks.each do |artwork| %>
                <tr>
                  <td><%= link_to image_tag(artwork.image.url(:thumb)), artwork %></td>
                  <td><%= artwork.title %></td>
                  <td><%= artwork.genre %></td>
                  <td><%= artwork.category %></td>
                  <td><%= artwork.medium %></td>
                  <td><%= artwork.date %></td>
                  <td><%= artwork.height %> x <%= artwork.width %></td>
                  <td><%= artwork.availability %> </td>
                  <td><%= artwork.rating %> </td>
                  <td><%= link_to 'Edit', edit_artwork_path(artwork) %></td>
                  <td></td>
                </tr>
              <% end %>
            </tbody>
          </table>
        </div>
      

      pages_controller.rb和artwork_controller.rb都有这样的代码:

      def index
          if params[:tag]
            @artworks = Artwork.tagged_with(params[:tag])
          else
            @artworks = Artwork.all
          end
        end
      

      pages_controller.rb:

      def home
          @artworks = Artwork.all
        end
      

      和routes.rb:

      get 'tagged' => 'artworks#index', :as => 'tagged'
      
        devise_for :users
        # get "artworks" => "artworks#index"
        # post "artworks" => "artworks#index"
      
        root "pages#home"
        get "about" => "pages#about"
        #get "users" => "users#index"
      
        resources :artworks
      

      提前感谢您的耐心和帮助!

3 个答案:

答案 0 :(得分:1)

这可能是正确的方法。但是你已经安装了设计并隐藏了链接。但是有人可以直接点击网址。您需要添加一些授权代码,这将使管理员只能编辑艺术作品。这可以通过多种方式完成。如果您有一个简单的应用程序,您只需添加一个前置过滤器,您可以在其中检查用户是否为管理员,然后只有他可以访问该页面并在编辑和更新操作时调用该页面。如果需要许多角色,您也可以使用像Authority这样的任何授权gem。希望这会有所帮助。

制作代码DRY:

before_filter :set_artworks, :only => [:home, :index]

private

 def set_artworks
  @artworks = Artworks.all
 end

答案 1 :(得分:0)

artwork / index.html.erb

<div class= 'row'> 
  <!-- your other source code goes here --> 
</div>

您希望此页面在用户登录前保密。然后您可以尝试:

<% if current_user.present? %> 
 <div class= 'row'> 
   <!-- your other source code goes here --> 
 </div>
<% end %>

此div仅在用户登录时才可见。对于尚未登录的用户,此页面将是私有的。

为了使编辑选项成为私有:

<% if current_user.present? %> 
  <div id="artworks" class="transitions-enabled">
    <% @artworks.each do |artwork| %>
        <div class="box">
          <%= link_to image_tag(artwork.image.url(:medium)), artwork %>
        </div>
    <% end %>
  </div>
<% end %>

在任何情况下,如果你想要公共/私人的几个部分,那么只需将它包装在视图的条件if语句中。

如果有人愿意,他可以直接点击网址并直接进入你的行动,在这种情况下你可以把条件放在控制器中。

 before_action :authenticate_user!, only: [:action_1, :action_2]

此外,如果您需要根据用户角色保密,您可以 总是选择cancan gem。

答案 2 :(得分:0)

维护权限的最简单方法是使用cancancan gem。

通过bundler安装并通过rails generate cancan:ability生成模型。然后你必须区分管理员用户和其他用户(例如你可以添加整数&#34;角色&#34;到用户模型)并在models/ability.rb#initialize

中写下这样的内容
if user.admin?
    can :manage, :all
else
    can :read, Artwork
end

并修改控制器,如下所示:

def index
authorize! :edit, Artwork
if params[:tag]
  @artworks = Artwork.tagged_with(params[:tag])
else
  @artworks = Artwork.all
end

结束

如果管理员用户不想转发索引,则会抛出异常。您可以使用redirect_to通知用户该错误。将其添加到ApplicationController:

rescue_from CanCan::AccessDenied do |exception|
    redirect_to root_url, :alert => exception.message
end