首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >RAILS:嵌套模型和回调中nil:NilClass的未定义方法‘`profile’

RAILS:嵌套模型和回调中nil:NilClass的未定义方法‘`profile’
EN

Stack Overflow用户
提问于 2012-07-09 08:44:59
回答 2查看 1K关注 0票数 0

这是一个实际的工作示例,我在上一篇文章中根据两位成员的要求对其进行了分解和简化,其中包含了更多细节。我提取并重写了这些代码,以解决持续两天的问题: nil:NilChass的未定义方法“配置文件”。

我使用gem "faker“和SQLite数据库浏览器,省略了控制器和视图,并专注于建模问题。

最初的问题出现在Goal.rb中,错误消息为:"undefined method‘`profile’for nil:NilClass“。根据SQLite DB Browser,已成功创建用户和配置文件记录。

问题出在Goal.rb模型下的一行"user.profile.lbm_lbs“。我不太明白为什么user.profile不存在,尽管user.profile是通过admin.profile =Profile.create!(名称...)创建的。填充(gem faker)应用包exec rake db: sample_data.rake

我之前发布的链接:RAILS: How to make new collection.build in a callback?

代码语言:javascript
复制
BffmModel::Application.routes.draw do
  resources :users do
    resource :profile
    resource :goal
    resource :tdee
    resources :progress_charts
  end
end

# == Schema Information
#
# Table name: users
#
#  id              :integer         not null, primary key
#  email           :string(255)
#  password_digest :string(255)
#  created_at      :datetime        not null
#  updated_at      :datetime        not null
#  remember_token  :string(255)
#

class User < ActiveRecord::Base
    attr_accessible :email, :email_confirmation, :password, :password_confirmation

    has_secure_password
    has_one :profile
    has_one :goal
    has_one :tdee
    has_many :progress_charts

    before_save { |user| user.email = email.downcase }
    before_save :create_remember_token

    VALID_EMAIL_REGEX = /\A[\w+\-.]+@[a-z\d\-.]+\.[a-z]+\z/i

    validates :email, :confirmation => true, :presence => true, 
                        length: { maximum: 50 },
                        format: { with: VALID_EMAIL_REGEX },
                        uniqueness: { case_sensitive: false }

    validates :email_confirmation, :presence => true
    validates :password, length: { minimum: 6 }
    validates :password_confirmation, presence: true

    private

        def create_remember_token
            self.remember_token = SecureRandom.urlsafe_base64
        end
end

# == Schema Information
#
# Table name: profiles
#
#  id               :integer         not null, primary key
#  name             :string(255)
#  surname          :string(255)
#  gender           :string(255)
#  date_of_birth    :date
#  body_weight_lbs  :integer
#  height_in_feets  :integer
#  height_in_inches :integer
#  bf_pct           :decimal(5, 2)
#  bf_lbs           :decimal(5, 2)
#  lbm_lbs          :decimal(5, 2)
#  user_id          :integer
#  created_at       :datetime        not null
#  updated_at       :datetime        not null
#

class Profile < ActiveRecord::Base
    attr_accessible :name, :surname, :gender, :date_of_birth, :body_weight_lbs,
                    :bf_pct, :height_in_feets, :height_in_inches
    belongs_to :user

    before_save :set_gender
    before_save :calculate_body_fat_lbs
    before_save :calculate_lean_body_mass_lbs

    private

        def set_gender
            if self.gender == "1"
                self.gender = "Male"
            elsif self.gender == "2"
                self.gender = "Female"
            end
        end

        def calculate_body_fat_lbs
            self.bf_lbs = ( self.bf_pct / 100 ) * self.body_weight_lbs
            self.bf_lbs = self.bf_lbs.round(0)
        end

        def calculate_lean_body_mass_lbs
            self.lbm_lbs = self.body_weight_lbs - self.bf_lbs
        end
end

# == Schema Information
#
# Table name: goals
#
#  id                    :integer         not null, primary key
#  desired_bf_pct        :decimal(, )
#  goal_type             :string(255)
#  ideal_body_weight_lbs :decimal(5, 2)
#  ideal_bfm_lbs         :decimal(5, 2)
#  fat_to_lose_lbs       :decimal(5, 2)
#  lbm_to_gain_lbs       :decimal(5, 2)
#  user_id               :integer
#  created_at            :datetime        not null
#  updated_at            :datetime        not null
#

class Goal < ActiveRecord::Base
  attr_accessible :desired_bf_pct, :goal_type

  belongs_to :user

  before_save :set_goal
  before_save :calculate_ideal_body_weight_lbs

  private

    def set_goal
      if self.goal_type == "1"
        self.goal_type = "Lose Fat"
      elsif self.goal_type == "2"
        self.goal_type = "Gain Muscles"
      end
    end

    def calculate_ideal_body_weight_lbs

      self.ideal_body_weight_lbs = user.profile.lbm_lbs / ( 1 - ( self.desired_bf_pct / 100 ) )
      self.ideal_body_weight_lbs = self.ideal_body_weight_lbs.round(0)
    end
end

/lib/task/sample_data.rake作为测试数据

代码语言:javascript
复制
namespace :db do
  desc "Fill database with sample data"
  task populate: :environment do
    admin = User.create!(email: "mikey@example.com",
                         email_confirmation: "mikey@example.com",
                         password: "foobar",
                         password_confirmation: "foobar")

    admin.profile = Profile.create!(name: "Michael",
                                    surname: "Colins",
                                    gender: "Male",
                                    date_of_birth: "1975-03-05",
                                    body_weight_lbs: 200,
                                    bf_pct: 25.5,
                                    height_in_feets: 5,
                                    height_in_inches: 11 )

    admin.goal = Goal.create!(  desired_bf_pct: 12,
                                goal_type: "Lose Fat")

    admin.tdee = Tdee.create!( tdee_calc_type: "Harris-Benedict",
                  activity_lvl: "BMR x 1.2")
  end
end

谢谢。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-07-09 10:00:30

代码语言:javascript
复制
admin.goal = Goal.create!(  desired_bf_pct: 12,
                            goal_type: "Lose Fat")

这条线快把你给绊倒了。

代码语言:javascript
复制
Goal.create!(  desired_bf_pct: 12,
               goal_type: "Lose Fat")

此部分将创建一个新的Goal。在此步骤中,不设置:user关系。这意味着Goal中的user方法将返回nil。因为nil没有profile方法,所以不能在保存user.profile之前从calculate_ideal_body_weight_lbs方法中调用Goal。使用已有的代码,您必须显式设置:user关系。

代码语言:javascript
复制
Goal.create!(  desired_bf_pct: 12,
               goal_type: "Lose Fat",
               user: admin )
票数 3
EN

Stack Overflow用户

发布于 2012-07-09 08:56:41

显然,user是零。你的问题让人觉得你不知道这一点。可能您没有登录,或者您不了解user方法的作用。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/11387925

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档