【问题标题】:Why do I get the error `undefined method 'map'`?为什么我会收到错误“未定义的方法 'map'”?
【发布时间】:2015-02-20 18:48:41
【问题描述】:

在我的 Ruby on Rails 应用程序中,我试图在 _form.html.erb 中显示三个下拉菜单,这些下拉菜单是从文件 _booking_lookup.html.erb 呈现的,并从模型中的下拉菜单方法中获取数据.

_form.html.erb:

<%= render(:partial => '/booking_lookup', :locals=> {:film => @film = Film.all, :showings => @showings = Showing.all, :seats => @seats = Seat.all, :my_path => '/films/booking_lookup' }) %>

_booking_lookup.html.erb:

<%= form_tag my_path, :method=>'post', :multipart => true do %>
<%= select_tag ('title_id'), 
    options_from_collection_for_select(@films, :id, :title_info, 0 ),
    :prompt => "Film" %>

<%= select_tag ('showings_id'), 
    options_from_collection_for_select(@showings, :id, :showing_times, 0 ),
    :prompt => "Showings" %> 

<%= select_tag ('seat_id'), 
    options_from_collection_for_select(@seats, :id, :seats_available, 0 ),
    :prompt => "Seats" %> 

<%= submit_tag 'Search' %>

电影.rb:

class Film < ActiveRecord::Base

has_many :showings
belongs_to :certificate
belongs_to :category

def title_info
     "#{title}"
end
end

座位.rb:

class Seat < ActiveRecord::Base
belongs_to :screen
has_many :bookings

def seats_available
    "#{row_letter}#{row_number}"
end
end

显示.rb:

 class Showing < ActiveRecord::Base
  belongs_to :film
  has_many :bookings
  belongs_to :screen

    def showing_times
        "#{show_date.strftime("%e %b %Y")} @ #{show_time.strftime("%H:%M")}"
    end
end

但由于某种原因,这条线:<%= select_tag ('title_id'), options_from_collection_for_select(@films, :id, :title_info, 0 ), :prompt => "Film" %> 我得到了错误:

NoMethodError in Bookings#new 
undefined method `map' for nil:NilClass

奇怪的是我在其他地方使用了很多这样的代码,我有一个 _multi_search.html.erb 表单:

 <%= form_tag my_path, :method=>'post', :multipart => true do %>
 <!--  Genre: -->
 Search By:
 <%= select_tag ('cat_id'), 
    options_from_collection_for_select(@categories, :id, :category_info, 0 ),
    :prompt => "Genre" %>

<%= select_tag ('cert_id'), 
    options_from_collection_for_select(@certificates, :id, :certificate_info, 0 ),
    :prompt => "Age Rating" %> 

<%= text_field_tag :search_string, nil, placeholder: "ACTOR" %>
or
<%= select_tag ('title_id'), 
    options_from_collection_for_select(@films, :id, :title_info, 0 ),
    :prompt => "Film" %>
<%= submit_tag 'Search' %>
<% end %>

并且在application.html.erb中使用:

&lt;%= render(:partial =&gt; '/multi_search', :locals=&gt; {:categories =&gt; @categories = existing_genres, :certificates =&gt; @certificates = Certificate.all, :films =&gt; @films = Film.all, :my_path =&gt; '/films/multi_find' }) %&gt;

而且效果很好。

我做错了什么?

【问题讨论】:

  • 你检查过@films 是否为 nil 吗?
  • 不,我没有,但我确信它不是零。奇怪的是,我在其他地方也有类似的工作,而且效果很好 - 我将把它包含在原始问题中。
  • @films nil - 你设置的是@film = Film.all,而不是@films = Film.all

标签: ruby-on-rails ruby ruby-on-rails-3 drop-down-menu


【解决方案1】:

看起来@films 为零。尝试在 _form.html.erb 中设置@films = Film.all(而不是@film = Film.all)。

更新

我建议将查询移至控制器操作。在模型-视图-控制器模式中,控制器应该向模型而不是视图询问数据。

# BookingLookupController
def new
  @films = Film.all
  @showings = Showing.all
  @seats = Seat.all
end

然后您可以在视图中引用实例变量。

<%= render partial: '/booking_lookup', locals: {films: @films, showings: @showings, seats: @seats, my_path: '/films/booking_lookup' } %>

【讨论】:

  • 我不敢相信我犯了那个错误。谢谢!
  • 有时只需要第二双眼睛。 =)
【解决方案2】:

在 Controller 中,选择您只想在下拉列表中显示名称的字段

def method_name
   @films = Film.select([:id, :title_info])
   @showings = Showing.select([:id, :showing_times])
   @seats = Seat.select([:id, :seats_available])
end

在页面中

<%= render(:partial => '/booking_lookup', :locals=> {:films => @films, :showings => @showings, :seats => @seats, :my_path => '/films/booking_lookup' }) %>

部分

 options_from_collection_for_select(films, :id, :title_info, 0 ),:prompt => "Film" %>

【讨论】:

  • 请使用控制器与模型通信。永远不要从视图中尝试这些类型的活动记录方法调用,这是一种非常糟糕的做法。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-01-30
  • 2017-01-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-04-23
相关资源
最近更新 更多