ruby 在为我的论坛构建消息/聊天时,nil:NilClass的未定义方法“message”

zqry0prt  于 2023-08-04  发布在  Ruby
关注(0)|答案(1)|浏览(69)

我一直试图实现一个聊天系统在我的论坛,它的工作。
但是当我想从以下位置更改路线时:

  • site/rooms/1到- site/rooms/name,但我发现了这个问题:
NoMethodError in RoomsController#show
undefined method `message' for nil:NilClass
Extracted source (around line #19):              
    @messages = @single_room.message.order(created_at: :asc)

字符串
聊天甚至不再工作了,我已经确定了房间控制器/显示的错误,但我不知道是什么原因导致的或如何修复它,我会给予你们与这个问题有关的代码
使用者

class User < ApplicationRecord
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :validatable

  has_many :posts
  has_one_attached :photo
  has_many :comments, dependent: :destroy
  acts_as_voter
  has_many :notifications, as: :recipient, dependent: :destroy

  scope :all_except, ->(user) {where.not(id: user)}
  after_create_commit {broadcast_append_to 'users'}
  has_many :messages

  def to_param
    username
  end

  def message
    @user = User.find(params[:id])
  end

  def increase_karma(count = 1)
    update_attribute(:karma, karma + count)
  end

  def decrease_karma(count = 1)
    update_attribute(:karma, karma - count)
  end

  validates :username, length: { in: 4..32 }, presence: true,
                      uniqueness: { case_sensitive: false }
  # validates :password, length: { minimum: 8 }
  # VALID_EMAIL_REGEX = /\A[\w+\-.]+@[a-z\d\-.]+\.[a-z]+\z/i.freeze
  # validates :email, presence: true, length: { maximum: 255 },
  #                   format: { with: VALID_EMAIL_REGEX },
  #                   uniqueness: { case_sensitive: false }
  # validates :admin_level, numericality: { only_integer: true,
  #                                         less_than_or_equal_to: 3 }
  # validates_numericality_of(:admin_level, only_integer: true, less_than_or_equal_to: 3)

  before_save { username.downcase! }
  before_save { email.downcase! }
  before_save :default_user
  def default_user
    self.admin_level = 1
  end
end


用户控制器

class UsersController < ApplicationController
  def show
    @user = User.find_by_username(params[:id])
  end

  def create
    @user = User.new(user_params)
    @user.user_id = current_user.id
    if @user.save
      redirect_to user_path(@user)
    else
      render :new, status: :unprocessable_entity
    end
  end

  def edit
    @user = User.find(params[:id])
  end

  def update
    @user = User.find(params[:id])
    if @user.update_attributes(user_params)
      flash[:success] = "User and oversight updated"
      redirect_to root_path
    else
      flash[:error] = "Something went wrong, please try again"
      render 'new'
    end
  end

  private

  def user_params
    params.require(:user).permit(:username, :email, :photo, :bio)
  end

  def get_name(user1, user2)
    user = [user1, user2].sort
    "private_#{user[0].id}_#{user[1].id}"
  end
end


房间

class Room < ApplicationRecord
  validates_uniqueness_of :name
  scope :public_rooms, -> { where(is_private: false) }
  after_create_commit { broadcast_if_public }
  has_many :messages
  has_many :participants, dependent: :destroy

  def to_param
    name
  end

  def broadcast_if_public
    broadcast_append_to 'rooms' unless is_private
  end

  def show
    @user = User.find_by_username(params[:id])
    @users = User.all_except(current_user)

    @room = Room.new
    @rooms = Room.public_rooms
    @room_name = get_name(@user, current_user)
    @single_room = Room.where(name: @room_name).first || Room.create_private_room([@user, current_user], @room_name)

    @message = Message.new
    @messages = @single_room.messages.order(created_at: :asc)
    render 'rooms/index'
  end

  def self.create_private_room(users, room_name)
    single_room = Room.create(name: room_name, is_private: true)
    users.each do |user|
      Participant.create(user_id: user.id, room_id: single_room.id)
    end
    single_room
  end
end


客房控制器

class RoomsController < ApplicationController
  before_action :authenticate_user!

  def index
    @room = Room.new
    @rooms = Room.public_rooms

    @users = User.all_except(current_user)
    render 'index'
  end

  def show
    @single_room = Room.find_by_name(params[:id])

    @room = Room.new
    @rooms = Room.public_rooms

    @message = Message.new
    @messages = @single_room.messages.order(created_at: :asc)

    @users = User.all.all_except(current_user)
    render 'index'
  end

  def create
    @room = Room.create(name: params["room"]["name"])
  end
end


信息内容

class Message < ApplicationRecord
  belongs_to :user
  belongs_to :room
  after_create_commit { broadcast_append_to room }
  before_create :confirm_participant

  def confirm_participant
    return unless room.is_private

    is_participant = Participant.where(user_id: user.id, room_id: room.id).first
    throw :abort unless is_participant
  end
end


消息控制器

class MessagesController < ApplicationController
  def create
    @message = current_user.messages.create(body: message_params[:body], room_id: params[:room_id])
  end

  private

  def message_params
    params.require(:message).permit(:body)
  end
end


我希望类可以识别方法,谢谢!

uqzxnwby

uqzxnwby1#

在你的 RoomsController 中,我猜你在将路由从site/rooms/id更改为site/rooms/name格式后忘记将params[:id]更改为params [:name],因为 params[:id] 值现在包含房间的 name 而不是 id

相关问题