undefined method `build' for nil:NilClass

hello, m following railcast http://media.railscasts.com/videos/073_complex_forms_part_1.mov

but i am getting error: undefined method `build' for nil:NilClass

can you please help

though m using belongs_to and has_one relationship rather then "has_many" is this the problem ???

if you want i can provide more details

thank you

hello, m following railcast http://media.railscasts.com/videos/073_complex_forms_part_1.mov

but i am getting error: undefined method `build' for nil:NilClass

If you look on the line in your code where the error occurs you will likely find that you are using something.build. The error is indicating the your 'something' is nil.

If you cannot see why it is nil it might be worth your while looking at the rails guide on debugging at http://guides.rubyonrails.org. This shows various methods of debugging your code. For example you can use ruby-debug to break into your code and inspect your data to see what the problem is.

Colin

hello colin, thanks for your reply, i know what that error means.... but my problem is why this is comming & how can i achieve my solution.

more details:

1) content_master model:

class ContentMaster < ActiveRecord::Base      has_one :Metadata end

2) metadata model:

class Metadata < ActiveRecord::Base     belongs_to :ContentMaster, :class_name => 'ContentMaster' end

3) new action in controller

def new     @content_master = ContentMaster.new     @metadata = @content_master.Metadata.build

    respond_to do |format|       format.html # new.html.erb       format.xml { render :xml => @content_master }     end end

4) oops same error undefined method `build' for nil:NilClass

i hope now my problem is more clear

looking forward for help

thank you

hello colin, thanks for your reply, i know what that error means.... but my problem is why this is comming & how can i achieve my solution.

Did you try my suggestion to use ruby-debug?

more details:

1) content_master model:

class ContentMaster < ActiveRecord::Base has_one :Metadata

That should be :metadata not :Metadata

end

2) metadata model:

class Metadata < ActiveRecord::Base belongs_to :ContentMaster, :class_name => 'ContentMaster'

That should be :content_master and then the class name will not be needed

end

3) new action in controller

def new @content_master = ContentMaster.new @metadata = @content_master.Metadata.build

Should be metadata again.

respond_to do |format| format.html # new.html.erb format.xml { render :xml => @content_master } end end

4) oops same error undefined method `build' for nil:NilClass

i hope now my problem is more clear

It might be worth your while having a look at the ActiveRecord Associations guide aswell as the debugging one. That will explain how to use associations.

Colin

thank you again for your reply

Did you try my suggestion to use ruby-debug?

i havent did that yet will do it as soon as possible and will report you back

> more details:

> 1) content_master model:

> class ContentMaster < ActiveRecord::Base > has_one :Metadata

That should be :metadata not :Metadata

> end

> 2) metadata model:

> class Metadata < ActiveRecord::Base > belongs_to :ContentMaster, :class_name => 'ContentMaster'

That should be :content_master and then the class name will not be needed

> end

> 3) new action in controller

> def new > @content_master = ContentMaster.new > @metadata = @content_master.Metadata.build

Should be metadata again.

though m beginner in Ruby as well as rails but i have read on some blog that rails just convert every simple simple and underscore words to camelCase( where required ) so it hardly matters how you write it, they are just conventions. Though i know it is good practise to follow conventions but i dont think it makes any error.

will do ruby debug ( for now i even dont now how to do this ) , and will post back about result or if i found something fruitful their

thank you

thank you again for your reply

Did you try my suggestion to use ruby-debug?

i havent did that yet will do it as soon as possible and will report you back

> more details:

> 1) content_master model:

> class ContentMaster < ActiveRecord::Base > has_one :Metadata

That should be :metadata not :Metadata

> end

> 2) metadata model:

> class Metadata < ActiveRecord::Base > belongs_to :ContentMaster, :class_name => 'ContentMaster'

That should be :content_master and then the class name will not be needed

> end

> 3) new action in controller

> def new > @content_master = ContentMaster.new > @metadata = @content_master.Metadata.build

Should be metadata again.

though m beginner in Ruby as well as rails but i have read on some blog that rails just convert every simple simple and underscore words to camelCase( where required ) so it hardly matters how you write it, they are just conventions. Though i know it is good practise to follow conventions but i dont think it makes any error.

I would very strongly suggest following the conventions, it will make your life much easier. Also I think that in this case it may at least in part be the cause of the problem. Consider the line @metadata = @content_master.Metadata.build What is Metadata here? In the model you have declared class Metadata < ActiveRecord::Base so Metadata is a class. But in the code you are using it as if it were a member of the ContentMaster class, which it is not, whereas metadata is (or at least could be, dependent on the table schema). I suggest that you make the changes I have proposed and try it.

Colin

I would very strongly suggest following the conventions, it will make your life much easier. Also I think that in this case it may at least in part be the cause of the problem. Consider the line @metadata = @content_master.Metadata.build What is Metadata here? In the model you have declared class Metadata < ActiveRecord::Base so Metadata is a class. But in the code you are using it as if it were a member of the ContentMaster class, which it is not, whereas metadata is (or at least could be, dependent on the table schema). I suggest that you make the changes I have proposed and try it.

i have tried all the conventions you told but it does no change in error ( hard luck ). I suppose their is lots and lots of chaos about rails conventions & defaults.

problem still remains unsolved !!!!!

thank you

I suppose their is lots and lots of chaos about rails conventions & defaults.

Not really...

problem still remains unsolved !!!!!

Post the new/modified code and we can have a look.

Post the new/modified code and we can have a look.

1) content_master model

class ContentMaster < ActiveRecord::Base     has_one :metadata end

2) metadata model:

class Metadata < ActiveRecord::Base      belongs_to :content_master end

3) def new     @content_master = ContentMaster.new     @metadata = @content_master.metadata.build

    respond_to do |format|       format.html # new.html.erb       format.xml { render :xml => @content_master }     end   end

4) still same error undefined method `build' for nil:NilClass

thank you

hello, i found this through google

"The create and build methods are only available for has_one/ belongs_to if an association already exist. It will not work when it's nil. "

http://dev.rubyonrails.org/ticket/535

though this is really a old post i dont know that it is solved or not.

thank you

i found this through google

"The create and build methods are only available for has_one/

belongs_to if an association already exist. It will not work when it’s

nil. "

http://dev.rubyonrails.org/ticket/535

though this is really a old post i dont know that it is solved or

not.

Well, doing their suggestion works.

def new

@content_master = ContentMaster.new @content_master.metadata = Metadata.new

respond_to do |format| format.html # new.html.erb format.xml { render :xml => @content_master } end end

Then just use @content_master.metadata in your new.html.erb or reassign it to @metadata, e.g.:

@metadata = @content_master.metadata = Metadata.new

The association is set up when you assign it to @content_master.metadata so you don’t need to call build from the nil object.

Cheers,

Andy

For a has_one, it seems you can user "build_<association>". So for your case:

@metadata = @content_master.build_metadata

...might do the job.

I like to leave this to the model where possible - if I *have* to have an associated object (or if I don't want to do loads of guards like "@content_master.metadata.attribute unless @content_master.metadata.nil?") I build/create the associated object after initialise.

#content_master model def after_initialize metadata ||= Metadata.new end

... it can cause problems in some cases, but can solve some in others! :slight_smile:

(a bit of advice gleaned from the "Refactoring: Ruby Edition" book)

thank you @Andy thank you @Michael

both method work in action new but comming back to problem as i was following http://media.railscasts.com/videos/073_complex_forms_part_1.mov

i need to create a virtual function in a model

i tried various combination (for * ) but failed

model:

class ContentMaster < ActiveRecord::Base

has_one :metadata

def meta_attribute=(meta_attribute)    *metadata = metadata.build(meta_attribute) end

end

i tried new and build_<assosiation> but they were not working ?? how to accomplish same in model

3) def new @content_master = ContentMaster.new @metadata = @content_master.metadata.build

      @metadata = @content_master.build_metadata

thank you for your reply @RickDeNatale

but solution u provided has allready been suggested.

my problem is now with defination of virtual function according to "has_one" relation

thank you anyway mac