以下是我在视图中的代码:show.html.erb
<ul>
<% @bullets.each do |r| %>
<li><%= r.content %></li>
<% end %>
</ul>
这是控制器中的代码:users_controller.rb
if cookies[:bullets].nil?
@bullets = Bullet.all.shuffle.first(4)
cookies[:bullets] = @bullets.collect(&:id)
else
@bullets = []
cookies[:bullets].each do |id|
@bullets << Bullet.find(id)
end
end
这将为nil返回未定义的方法'each':
上的NilClass<% @bullets.each do |r| %>
我想知道为什么会这样做,如何修复它以从名为“bullets”(列为内容)的数据库(sqlite3)表中发布四个随机固定项目内容。
编辑:这是整个控制器:
class StudentsController < ApplicationController
#GET /
def index
@students = Student.all
respond_to do |format|
format.html # index.html.erb
format.json { render json: @students }
end
end
#GET /new
def new
@student = Student.new
end
#POST
def create
@student = Student.new(params[:student])
if @student.save
render :file => 'app/views/success'
else
render :file => 'app/views/students/fail'
end
end
#GET /students/{:id}
def show
@student = Student.find_by_url(params[:id])
respond_to do |format|
format.html # show.html.erb
format.json { render json: @student }
end
end
#BULLETS Randomizing /students/new.html.erb
if cookies[:bullets].nil?
@bullets = Bullet.all.shuffle.first(4)
cookies[:bullets] = @bullets.collect(&:id)
else
@bullets = []
cookies[:bullets].each do |id|
@bullets << Bullet.find(id)
end
end
#GET /students/1/edit
def edit
@student = Student.find_by_url(params[:id])
end
def update
@student = Student.find_by_url(params[:id])
respond_to do |format|
if @student.update_attributes(params[:student])
format.html { redirect_to @student, notice: 'Student was successfully updated.'}
else
format.html { render action: "edit" }
format.json { render json: @student.errors, status: :unprocessable_entity }
end
end
end
#DELETE
def destroy
@student = Student.find_by_url(params[:id])
@student.destroy
respond_to do |format|
format.html { redirect_to students_url }
format.json { head :no_content }
end
end
end
编辑#2:像这样?
#GET /students/{:id}
def show
@student = Student.find_by_url(params[:id])
#BULLETS Randomizing /students/show.html.erb
if cookies[:bullets].nil?
@bullets = Bullet.all.shuffle.first(4)
cookies[:bullets] = @bullets.collect(&:id)
else
@bullets = []
cookies[:bullets].each do |id|
@bullets << Bullet.find(id)
end
end
respond_to do |format|
format.html # show.html.erb
format.json { render json: @student }
end
end
答案 0 :(得分:2)
看起来应该是:
#GET /students/{:id}
def show
@student = Student.find_by_url(params[:id])
#BULLETS Randomizing /students/new.html.erb
if cookies[:bullets].nil?
@bullets = Bullet.all.shuffle.first(4)
cookies[:bullets] = @bullets.collect(&:id)
else
# simpler to use an 'in list' for only 4 id's
Bullet.where("id in (?)", cookies[:bullets])
end
respond_to do |format|
format.html # show.html.erb
format.json { render json: @student }
end
end
注意我将你的cookies
数组上的循环转换为带有'in list'的单个语句 - 这应该简化为查找生成的sql。
尽管如此,这个代码应该被推入模型中是有争议的:
class Bullet < ActiveRecord::Base
NUM_USER_BULLETS = 4
# fetch a random set of
def self.user_bullets
Bullet.all.shuffle.first(NUM_USER_BULLETS)
end
end
或类似的东西。然后你的控制器更简单:
#GET /students/{:id}
def show
@student = Student.find_by_url(params[:id])
#BULLETS Randomizing /students/new.html.erb
if cookies[:bullets].nil?
@bullets = Bullet.user_bullets
cookies[:bullets] = @bullets.collect(&:id)
else
# simpler to use an 'in list' for only 4 id's
Bullet.where("id in (?)", cookies[:bullets])
end
respond_to do |format|
format.html # show.html.erb
format.json { render json: @student }
end
end
将代码迁移到您的模型中,您的控制器就更简单了。
答案 1 :(得分:1)
class StudentsController < ApplicationController
before_filter :get_bullets, :only => [:show]
def show
end
...
protected
def get_bullets
#BULLETS Randomizing /students/new.html.erb
if cookies[:bullets].nil?
@bullets = Bullet.all.shuffle.first(4)
cookies[:bullets] = @bullets.collect(&:id)
else
@bullets = []
cookies[:bullets].each do |id|
@bullets << Bullet.find(id)
end
end
end
end
答案 2 :(得分:1)
我建议将“随机项目符号”代码重构为before_filter
show
动作并在数据库中执行随机化,这比加载整个表格并执行随机化更快红宝石:
class UsersController < ApplicationController
before_filter :assign_bullets, :only => :show
# ...
private
def assign_bullets
if cookies[:bullets]
@bullets = cookies[:bullets].map { |id| Bullet.find(id) }
else
@bullets = Bullet.order('RANDOM()').limit(4)
cookies[:bullets] = @bullets.map(&:id)
end
end
end