我在1:N
和user
模型之间有post
个关系。我想访问user_id
模型中的post
。我是通过访问current_user
来尝试的,但它正在投掷找不到current_user
变量。
我的userModel类:
class User < ActiveRecord::Base
devise :database_authenticatable, :registerable, :validatable
has_many :post
validates_format_of :email, with: /\A([^@\s]+)@((?:[-a-z0-9]+\.)+[a-z]{2,})\Z/i
end
MyPostModel类:
class Post < ActiveRecord::Base
belongs_to :user
before_create :fill_data
validates_presence_of :name, :message => 'Name field cannot be empty..'
def fill_data
self.is_delete = false
self.user_id = current_user # here I am getting the error
end
end
MyPostController类
class PostController < ApplicationController
before_action :authenticate_user!
def index
@post = Post.all
end
def new
@post = Post.new
end
def create
@post = Post.new(post_params)
if @post.save
redirect_to action: 'index'
else
render 'new'
end
end
.....
private
def post_params
params.require(:post).permit(:name,:user_id,:is_delete)
end
end
我可以访问Post控制器中的before_action :authenticate_user!
,但不能访问current_user
或post model
中的controller
。我在Post.fill_data. self.user_id
中做错了什么?
其余的代码工作正常,我可以在sqlite3数据库中看到:name and :is_delete
的新条目(当我在Post类中评论self.user_id行时)。
我已经拥有post
class CreatePosts < ActiveRecord::Migration
def change
create_table :posts do |t|
t.string :name
t.boolean :is_delete
t.references :user, index: true, foreign_key: true
t.timestamps null: false
end
end
end
答案 0 :(得分:1)
在Rails中,您的模型不应该知道当前用户或任何其他状态的应用程序。他们只需要知道自己和他们直接相关的对象。
另一方面,控制器知道当前用户。
所以正确的方法是从Post中删除fill_data
回调。并在控制器中执行:
class PostController < ApplicationController
before_action :authenticate_user!
def index
@post = Post.all
end
def new
@post = current_user.posts.build
end
def create
@post = current_user.posts.build(post_params)
if @post.save
redirect_to action: 'index'
else
render 'new'
end
end
private
def post_params
params.require(:post).permit(:name,:user_id,:is_delete)
end
end
您还应该为数据库中的is_delete
列设置默认值,但如果您想像专业人士那样使用enum代替。
创建迁移rails g migration AddStateToUsers
并填写:
class AddStateToUsers < ActiveRecord::Migration
def change
add_column :users, :state, :integer, default: 0
remove_column :users, :is_delete
add_index :users, :state
end
end
然后我们使用rails enum宏将状态映射到符号列表:
class Post
enum state: [:draft, :published, :trashed]
# ...
end
这样,您就可以Post.trashed
获取垃圾箱或post.trashed?
中的所有帖子,以检查特定帖子是否已被删除。
请注意我使用trashed
而不是删除,因为ActiveRecord构建了我们不想搞砸的deleted?
方法。
答案 1 :(得分:0)
您正尝试使用before_create回调在post模型中添加current_user.id。但最好的办法是使用这个
在posts_controller.rb
中def new
@post = current_user.posts.new
end
def create
@post = current_user.posts.create(posts_params)
end
这将为当前用户创建一个帖子。
您的fill_data方法将是
def fill_data
self.is_delete = false
end