Announcement (2017-05-07): www.ruby-forum.com is now read-only since I
unfortunately do not have the time to support and maintain the forum any
more. Please see rubyonrails.org/community and ruby-lang.org/en/community
for other Rails- und Ruby-related community platforms.

Now I have 3 models, item category and sub-category
and 3 Tables in my database.
I planed to set the association like this.
Item
Belongs_to :category
Belongs_to :sub-category
category
Has_many :items
Has_many :sub_category
sub_category
belongs_to :category
Has_many :items
And now I want to have some dynamic drop down list in the items/new
page
When I chose one category, and the sub-category will dynamically
updated.
what other move do I need?
Is that right? It makes me feel confused with these associations.

Jette Chan wrote:
> Now I have 3 models, item category and sub-category> and 3 Tables in my database.>> I planed to set the association like this.>> Item> Belongs_to :category> Belongs_to :sub-category>> category> Has_many :items> Has_many :sub_category>> sub_category> belongs_to :category> Has_many :items>> And now I want to have some dynamic drop down list in the items/new> page> When I chose one category, and the sub-category will dynamically> updated.> what other move do I need?>> Is that right? It makes me feel confused with these associations.
category.rb
has_many :sub_categories
has_many :items ,:through=>:sub_categories
sub_category.rb
belongs_to :category
has_many :items
item.rb
belongs_to :sub_category
by use of this association you can define get any of 2 by select of any
of 1 among three models
for that use Ajax Updater

A subcategory is always a child of a category. Lets set up your
associations
as such. It will use only one db column instead of two. Each item will
belong
to a subcategory; each subcategory will belong to a category. It will
look
something like this:
Category
/ \
Subcategories
/ | \
Items Items Items
We will use ActiveRecord's :through association. Your models will look
like
this:
Class Category
has_many :subcategories
has_many :items, :through => :subcategory
Class Subcategory
has_many :items
Class Item
belongs_to :subcategory
When you do this, Category will associate with an Item by tunneling
through
Subcategory. These helpful methods will now be available:
Item.category
Item.subcategory
Subcategory.category
Category.items
Category.subcategories
Subcategory.items
Now, we need to do your drop down list (called a "select" in Rails)
magic. I'm
not much of a Javascript buff, so this is a dirty little hack that
*should*
work. The idea is to have the "subcategory" select contained in a DIV.
The
contents on the DIV will originate from an action that only deals with
creating that select, likewise it will render a partial containing only
the
select's markup. We'll have an observer watch the "category" select, and
send
whatever it changes to to the "subcategory" select handler, which will
in
turn re-render the select with the appropriate contents. Your
controller,
model, view, and partial should look like this:
Item Controller:
def subcategory_handler
@subcategories = Category.find(params[:category_id]).subcategories
render :partial => "subcat_select", :locals => {:s =>
@subcategories}
end
### put this in the method "new":
@category = Category.find :all
@subcategories = @category[0].subcategories
Item model:
### add this virtual attribute, so that we don't get NoMethod errors:
attr_accessor :category_id
Partial _subcat_select.html.erb
<%= select "item", "subcategory_id", s.collect {|s| [ s.name, s.id ]
} -%>
View for Item#new:
(I assume that the values in your select options are the category and
subcategory IDs.)
<label>Category</label>
<%= select "item", "category_id", @category.collect {|c| [ c.name,
c.id ] }, { }, { :id => "category" } -%>
...
<label>Subcategory</label>
<div id="subcategory_container">
<%= render :partial => "subcat_select", :locals => {:s =>
@subcategories} -%>
</div>
...
(This must be called AFTER your select fields are defined!)
<%= observe_field :category, :url => { :action
=> :subcategory_handler }, :with => :category_id, :update
=> "subcategory_container" %>
That's a pretty rough hack, but I tested it on Rails 2.1.0 and it works.
It'll
take some fine tuning on your part. There might be a completely
different way
of handling such a thing, this is only one option to explore.
Hope it makes sense.