Forum: Ruby on Rails One Controller, Many models

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.
71b39cce77a48a3f99b4e6a14a656007?d=identicon&s=25 Peer Allan (Guest)
on 2006-04-14 07:05
Hello all,

I am working on a app right now that is going to replace a paper form
process out client has.  This process has quite a few forms (about 30)
and different groups of forms (section) need to be filled out based on
what information is required from the user.  For example, here is a
possible process of 2 users:

user 1         user 2
Section 1      Section 1
Section 2      Section 2
Section 12     Section 3
Section 13     Section 8
Section 15     Section 15

I am trying to figure out the most efficient way to do this in Rails.  I
know I could just scaffold all the section tables, but then I would have
30 controllers for 30 models that are doing pretty similar things. I
believe that I will make the models for each section to allow for
customization in terms of validation and such, but I feel there must be
a way to avoid 30 controllers.  Especially when each one will only
differ by which model it is using.

What I would like to do is define the sections and their order for each
"track"., then have a controller pull up the correct section model
depending on where the user is in the process.

I am still getting the hang of Rails and application architecture/domain
model stuff has always been a weakness. Any help or direction on how to
handle this problem would be greatly appreciated.  (any recommendations
on some good places/books to learn software architecture would be nice
to)

Thanks

Peer
43ec5998360a0cc21b51afef1781e9c0?d=identicon&s=25 Daniel Higginbotham (Guest)
on 2006-04-14 08:34
(Received via mailing list)
Hi Peer,

I would take a look at single table inheritance
(http://wiki.rubyonrails.org/rails/pages/SingleTabl...) to see
if
it helps solve your problem.  Also, it's pretty simple to load other
models
into your controller. If you want to load and use the model in
"app/models/some_model.rb" you'd use something like

def track
	require 'some_model'
	section_1 = SomeModel.new()
	section_1.save
end

Validation would still reside in your models like normal.

Additionally, to avoid duplicating controller code across many
controllers
you can put it into app/controllers/application.rb .

I hope this helps!

Daniel
71b39cce77a48a3f99b4e6a14a656007?d=identicon&s=25 Peer Allan (Guest)
on 2006-04-14 14:24
Hi Daniel,

Unfortunately I don't see how STI will help me in this case as each form
(model) has very different information. If I were to put them in a
single table it would have well over 100 columns. This is assuming that
you are talking about STI for all the models.  If not, could you please
describe how I could use STI?

Peer

Daniel Higginbotham wrote:
> Hi Peer,
>
> I would take a look at single table inheritance
> (http://wiki.rubyonrails.org/rails/pages/SingleTabl...) to see
> if
> it helps solve your problem.  Also, it's pretty simple to load other
> models
> into your controller. If you want to load and use the model in
> "app/models/some_model.rb" you'd use something like
>
> def track
> 	require 'some_model'
> 	section_1 = SomeModel.new()
> 	section_1.save
> end
>
> Validation would still reside in your models like normal.
>
> Additionally, to avoid duplicating controller code across many
> controllers
> you can put it into app/controllers/application.rb .
>
> I hope this helps!
>
> Daniel
34f5b045aec62235c17458650ea75353?d=identicon&s=25 Steve Koppelman (hatless)
on 2006-04-14 16:38
Models don't need to have their own controllers or full-blown scaffolds.
Nothing is stopping you from having one user-accessible controller and
one admin controller, for instance, and any controller can access any
model.

And as long as you're careful about security in the controller, there's
nothing wrong with having a single "edit" action in that one big
controller that takes a Secton as an argument and presents an
appropriate partial, for instance.

Peer Allan wrote:
> Hello all,
>
> I am working on a app right now that is going to replace a paper form
> process out client has.  This process has quite a few forms (about 30)
> and different groups of forms (section) need to be filled out based on
> what information is required from the user.  For example, here is a
> possible process of 2 users:
>
> user 1         user 2
> Section 1      Section 1
> Section 2      Section 2
> Section 12     Section 3
> Section 13     Section 8
> Section 15     Section 15
>
> I am trying to figure out the most efficient way to do this in Rails.  I
> know I could just scaffold all the section tables, but then I would have
> 30 controllers for 30 models that are doing pretty similar things. I
> believe that I will make the models for each section to allow for
> customization in terms of validation and such, but I feel there must be
> a way to avoid 30 controllers.  Especially when each one will only
> differ by which model it is using.
>
> What I would like to do is define the sections and their order for each
> "track"., then have a controller pull up the correct section model
> depending on where the user is in the process.
>
> I am still getting the hang of Rails and application architecture/domain
> model stuff has always been a weakness. Any help or direction on how to
> handle this problem would be greatly appreciated.  (any recommendations
> on some good places/books to learn software architecture would be nice
> to)
>
> Thanks
>
> Peer
8d30b78dcd3ae8ff8d5e6085059060c7?d=identicon&s=25 Martin Bernd Schmeil (thebernd)
on 2006-04-14 16:56
I'm not sure if I exactly understood what you want. So my suggestion is
short and maybe doesn't fit your needs (also it's definitly hackerish,
might be unsecure and there might be smarter ways to accomplish the same
task, forgive me, I'm relatively new to Ruby and RoR).

We needed an editor to internationalize several lookup tables (which had
some common fields, i.e. the different translations). Some of them had
parent relations. Instead of having a zillion views (and controllers) we
introduced two methods to each model parent_class() and parent_key()
returning the names to access the parent class / table (or nil in case
of a parent table).

Then we were passing the Model name (e.g. from a form) to the controller
and instanciated the corresponding objects with

def klazz
  Object.instance_eval(params[:model]).find(params[:id])
end

def parent_klazz(object)
  Object.instance_eval(object.parent_class)
end

This in addition with the parent_key method should give you all options
to make such issue generic. Let me know if you need more info.

Note: This might contain errors, I didn't compare this with the actual
code...
71b39cce77a48a3f99b4e6a14a656007?d=identicon&s=25 Peer Allan (Guest)
on 2006-04-14 19:43
Thanks for everyone's suggestions.  I have a couple of ideas that I am
going to experiment with.  I have a feeling that this question is not
that difficult to answer, but I am looking for a more complicated
solution because it seems complicated.

Peer

Martin Bernd Schmeil wrote:
> I'm not sure if I exactly understood what you want. So my suggestion is
> short and maybe doesn't fit your needs (also it's definitly hackerish,
> might be unsecure and there might be smarter ways to accomplish the same
> task, forgive me, I'm relatively new to Ruby and RoR).
>
> We needed an editor to internationalize several lookup tables (which had
> some common fields, i.e. the different translations). Some of them had
> parent relations. Instead of having a zillion views (and controllers) we
> introduced two methods to each model parent_class() and parent_key()
> returning the names to access the parent class / table (or nil in case
> of a parent table).
>
> Then we were passing the Model name (e.g. from a form) to the controller
> and instanciated the corresponding objects with
>
> def klazz
>   Object.instance_eval(params[:model]).find(params[:id])
> end
>
> def parent_klazz(object)
>   Object.instance_eval(object.parent_class)
> end
>
> This in addition with the parent_key method should give you all options
> to make such issue generic. Let me know if you need more info.
>
> Note: This might contain errors, I didn't compare this with the actual
> code...
This topic is locked and can not be replied to.