1

In our application, many resources are nested under a common resource representing an organization. Most URLs include an organization ID the following pattern: /:organization_id/notifications/:id.

My problem is that I always have to give the current organization to generate the URL to any model. For example, the link to an existing notification would be link_to [@organization, @notification].

Since a notification already belongs to an organization, I was wondering if it was possible to generate my URL using link_to @notification and it would actually generate a URL including the organization ID of the notification. I was hoping that a configuration in the model would be able to achieve this but I could not find anything in the guides, the docs or the source code of Rails.

I would like to keep the organization ID visible in the URL as this is an information that is used by our customers. So I do not want to use shallow nested resources for this problem.

We are using Rails 5.2.0.

Vincent Robert
  • 35,564
  • 14
  • 82
  • 119
  • Sorry I posted a wrong answer as you want to keep organization id in the URL. Just get the organization from the notification variable like `link_to some_notification_path(@notification.organization.id, @notification.id)` Then you write the helper with the `@notification` variable only. (this work only if Notification is a direct child of Organization, if not, you have to grab the whole tree, or make a `through:` child) – Maxence May 19 '18 at 15:46
  • Helpers are a solution, an ugly one but a solution. This would require a lot of boilerplate code to work with forms for example. The route solution is better and allows me to fine-tune the URL for any model depending on its data. Nice. – Vincent Robert May 19 '18 at 23:25

1 Answers1

2

You want the resolve route definition method.

It is designed to do exactly what you want: configure a different behaviour when a single model instance is passed to url_for (as link_to does, for example).

Specifically, in your config/routes.rb, something like:

resolve("Notification") do |note|
  [:notification_organization, note.organization, note]
end

It sounds like you were on the right track -- it's just a routing concern rather than a model one.

matthewd
  • 4,332
  • 15
  • 21
  • 1
    I'm not sure exactly what functionality ended up shipping, so I'll leave this out of the answer for now, but it may also work as just `[note.organization, note]` -- without the explicit route name symbol. – matthewd May 19 '18 at 16:02
  • This is exactly what I was looking for. Too bad that it does not work with complex URL for now, but this will solve a lot of my problems. Thanks. – Vincent Robert May 19 '18 at 23:20