1

I'm using ActiveResource to pull objects from an internal API

This API has the following(simplified):

class Project < ApplicationRecord
  has_many :contributions
  ...
end

class Contribution < ApplicationRecord
  belongs_to :project
  belongs_to :user
  ...
end

class User < ApplicationRecord
  has_many :contributions
  ...
end

and routes so contributions can only be created associated to a project

resources :projects, except: [:new, :edit] do
  resources :contributions, except: [:new, :edit, :destroy]
end

resources :users, except: [:new, :edit] do
  resources :contributions, only: [:index, :show]
end

resources :contributions, only: [:index, :show, :update]

Is it possible to submit a dynamic prefix so that I can hit these paths selectively? i.e. projects/:project_id/contributions on create, but /contributions on index (all).

EDIT:

My active resources all look like so:

class Contribution < ActiveResource::Base
  self.site = "#{base_url}/api/v1/"
  self.headers['Authorization'] = "Token token=\"#{TokenGenerator}\""
  ...
end

Not much customization there.

My biggest concern is the create post which I would like to always be nested inside a project.

At the moment I'm checking params in the /contributions route to see if there is any viable 'parent_id' in them, and figuring out if said parent exists.

I'm guessing the gem was not designed with the idea of a resource having multiple routes. I can always include:

class Project  ActiveResource::Base
  self.site = "#{base_url}/api/v1/"
  self.headers['Authorization'] = "Token token=\"#{TokenGenerator}\""
  ...
  def contributions
    Contributions.all(params: {project_id: id})
  end
end

inside Projects.rb and make sure the API controller knows how to handle parents if they exist, but only because I have access to the source of both the API and the consumer app.

worth asking too: Am I just over complicating this?

aelosada
  • 21
  • 3
  • Not sure, if I understood your question correctly, but maybe you're asking about [polymorphic routes](https://api.rubyonrails.org/v5.2.1/classes/ActionDispatch/Routing/PolymorphicRoutes.html)? – Vasilisa Oct 18 '18 at 14:59
  • what do you mean with "hit these paths selectively"? – arieljuod Oct 18 '18 at 15:29
  • 1
    It would be useful for you to post your ActiveResource models as well, or, at least, the skeleton of them so we can get an idea of what you're intending. It _sounds_ like you want to use a single ActiveResource model to hit any the routes depending on some criteria. My gut instinct is to have your ActiveResource models map more closely to the exposed API, such that a `Contribution` are created with the related `Project` (which, I assume, `accepts_nested_attributes_for :contributions`) – Chris Hall Oct 18 '18 at 15:55
  • @Vasilisa thanks but these are not polymorphic resources. – aelosada Oct 18 '18 at 20:17
  • @arieljuod I would like my resource to be created with a `post` to the prefix `projects/:project_id/contributions` while being able to call on a get on the following `/contributions`, `projects/:project_id/contributions`, `users/:user_id/contributions` depending on the circumstance. – aelosada Oct 18 '18 at 20:20
  • @ChrisHall I've added one of the active resources on the consuming side, but they have nothing much outside of the ordinary. The thing with creating `Contributions` along with its parent `Project` is that they are never created at the same time: a project has to be approved and published before any contributions can be made. – aelosada Oct 18 '18 at 20:30
  • The [documentation for ARes](https://github.com/rails/activeresource) states that "Connection settings (`site`, `headers`, `user`, `password`, `proxy`) and the connections themselves are store in thread-local variables to make them thread-safe, so you can also set these dynamically". So, you should be able to change the value of `site` as necessary. On the other hand, creating a Contribution specifically through the project route isn't strictly necessary as long as you're requiring the project_id. If you can, I would suggest just allowing create on the normal Contribution route. – Chris Hall Oct 18 '18 at 21:41
  • @ChrisHall I actually thought of something: you could use a `before_create` filter to override the site. But at the end of the day, I think I'll keep it simple and just post to the base `/contributions` route and validate existence of the parent in the controller. – aelosada Oct 18 '18 at 22:04

0 Answers0