RoR项目create动作出现undefined method错误求助
问题描述
在Ruby on Rails项目中提交Tweet新增表单时触发undefined method 'tweet' for #<Tweet:0x00007f64b90ad988>错误,其他功能均正常。以下是相关代码及报错信息:
TweetsController代码
class TweetsController < ApplicationController before_action :set_tweet, only: [:show, :update, :destroy] before_action :authenticate_user!, only: [:new, :index, :show, :create] def new @tweet = current_user.tweets.build end def index @tweets = Tweet.all end def show @tweet = Tweet.find(params[:id]) end def create @tweet = current_user.tweets.build(tweet_params) respond_to do |format| if @tweet.save format.html { render notice: 'Tweet was successfully created.' } format.json { render :show, status: :created, location: @tweet } else format.html { render :new } format.json { render json: @tweet.errors, status: :unprocessable_entity } end end end def destroy @tweet = Tweet.find(params[:id]) @tweet.destroy respond_to do |format| if @tweet.destroy format.html { render notice: 'Tweet was successfully removed.' } format.json { render :index, status: :destroyed, location: @tweet } end end end private def set_tweet @tweet = Tweet.find(params[:id]) end def tweet_params params.require(:tweet).permit(:user_id, :content) end end
表单代码
<%= simple_form_for @tweet do |f| %> <%= f.label :content %> <%= f.text_field :content %> <br><br> <%= f.submit %> <% end %>
报错信息
提交表单时,在create动作的@tweet.save行出现错误:undefined method tweet' for #Tweet:0x00007f64b90ad988`
日志详情:
Started POST "/tweets" for ::1 at 2020-03-19 12:33:19 +0000 Processing by TweetsController#create as HTML Parameters: {"authenticity_token"=>"qHs3m6KUuUb2nA3w+o4T7C7xTm+6f8iPHEv6ur4UvLs+fu+OAMgxCSVkGM0tBxjfzS/36HoTpEil9R+SQW/sfA==", "tweet"=>{"content"=>"cdzcdzc"}, "commit"=>"Create Tweet"} User Load (1.8ms) SELECT "users".* FROM "users" WHERE "users"."id" = ? ORDER BY "users"."id" ASC LIMIT ? [["id", 2], ["LIMIT", 1]] Completed 500 Internal Server Error in 16ms (ActiveRecord: 1.8ms | Allocations: 5089) NoMethodError (undefined method `tweet' for #<Tweet:0x00007f1d189b2490>): app/controllers/tweets_controller.rb:23:in `block in create' app/controllers/tweets_controller.rb:22:in `create'
分析与解决方案
这个错误的核心原因是Tweet模型中存在错误的关联定义,导致调用@tweet.save时,ActiveRecord试图执行一个不存在的tweet方法。
1. 检查并修正Tweet模型的关联
首先打开你的app/models/tweet.rb文件,确保关联定义正确:
# app/models/tweet.rb class Tweet < ApplicationRecord belongs_to :user # 这里应该关联到User,而不是其他错误的模型 end
你很可能不小心在这里写了belongs_to :tweet(这会让ActiveRecord尝试在Tweet表中找tweet_id字段并生成tweet方法),而不是正确的belongs_to :user。
2. 确认User模型的关联正确
同时检查app/models/user.rb,确保用户和推文的一对多关联正确:
# app/models/user.rb class User < ApplicationRecord has_many :tweets, dependent: :destroy # 用户拥有多个推文,删除用户时同时删除推文 end
3. 修复控制器中的小问题
虽然这不是当前报错的原因,但你的控制器里有两个小问题可以顺便修正:
- create动作的成功响应:用
redirect_to代替render,因为render会停留在当前请求上下文,而正确的做法是重定向到推文详情页或列表页:if @tweet.save format.html { redirect_to @tweet, notice: 'Tweet was successfully created.' } # ...其他代码保持不变 - destroy动作重复调用destroy:你在destroy方法里两次调用了
@tweet.destroy,这会导致第二次调用时对象已经被销毁,引发错误,修正为:def destroy @tweet.destroy respond_to do |format| format.html { redirect_to tweets_url, notice: 'Tweet was successfully removed.' } format.json { head :no_content } end end
完成以上修正后,重启服务器再测试新增推文功能,应该就能正常工作了。
内容的提问来源于stack exchange,提问作者davidm
相关产品推荐
相关产品推荐

