link_to within model

My task model has the following function:

class Task < ActiveRecord::Base   belongs_to :user   belongs_to :project   belongs_to :person

  ... stuff ...

  def summary     '<b>' + user.firstname + ' ' + due.strftime('%m/%d') + ':</b> ' +     '<a href="' + url_for(:action => "edit", :id => id) + '">' + name + '</a>'   end end

... which is used elsewhere by doing something like this:

project.tasks.find(:all, :conditions => 'completed = 0').collect{|p| p.summary}.join(',<br/> ')

... which is then used for display, to show all the tasks associated with a particular project, with each task being a hyperlink that the user can click to open that particular task. ('Edit' at the moment 'cause I don't yet have a show.)

The problem is, url_for and link_to both generate errors when put there (it works fine without that part). And it doesn't seem to work right in the helper either.

What's the right way to do this?

Thanks, Sai

Many MVC hardcases would say that HTML in the model or controller is not a good idea. Helpers and partials are a better way to go in terms of readability.

I have been trying hard to learn rails, be DRY and impliment the philosophy behind the framework. As such I have used the following approach in my latest project:

Firstly, read the following: Buckblog: Skinny Controller, Fat Model. I found this approach has improved the readability and understandability of my code greatly.

So, I would change: project.tasks.find(:all, :conditions => 'completed = 0').collect{|p| p.summary}.join(',<br/> ')

to something like: @projects = Project.tasks.not_completed

Then create a model method to respond: def self.not_completed   project.tasks.find(:all, :conditions => 'completed = 0') end

Then in the view you can: <%= render :partial => "/project/link", :collection => @projects %>

and finally, create a partial to display each uncompleted task: <b>   <%= link.user.firstname %> <%= due.strftime('%m/%d') %> </b> <%= link_to (link.name, :controller =>"project", :action => "edit", :id => link.id) %> </a>

I am sure this code will not work without a few tweaks (like I said, I am learning), but it's one way to achieve what you need. I am sure another guru will enlighten us both further....

Or else You can just directly change your stuff:

def summary     '<b>' + user.firstname + ' ' + due.strftime('%m/%d') + ':</b> ' +     '<a href="' + url_for(:action => "edit", :id => id) + '">' + name + '</a>'   end

LIKE THIS:

def summary     '<b>' + user.firstname + ' ' + due.strftime('%m/%d') + ':</b> ' +     link_to (name, :action => "edit", :id => id)   end

def summary     '<b>' + user.firstname + ' ' + due.strftime('%m/%d') + ':</b> ' +     link_to ("#{name}", :action => "edit", :id => id)   end

This doesn't work - try it. Both url_for and link_to generate "method undefined" errors when put in the model file.

As for MVC - yes, it'd be better to put it in a view, but I'm using this with AjaxScaffold and therefore just want to generate a clip that gets sent as the column value (i.e. for table 'projects', column 'tasks', it calls this [plus some other stuff] to fill the column).

It works if I hardcode it, i.e. http://foo/control/action/number but that's really ugly. I'd like to get link_to to work. instead.

The following should work:

Try to define the same in a helper by using CONTENT_TAG

def summary   content << content_tag('div', '<b>' + user.firstname + ' ' + due.strftime('%m/%d') + ':</b> ' + link_to ("#{name}", :action => "edit", :id => id) )   end