3

I'm building a Rails app that is probably going to have a large amount of models. For now let's say that i need to have Users, and each User will have a personal Blog

I've been developing the User-related part on a separate Engine (let's call it AuthEngine) that encapsulates the User model, authentication, etc. At the time this seemed like the best approach

In parallel, my colleague was developing another engine, to deal with the blog features (let's call it BlogEngine). Now he needs to access user data which is stored in the other engine. He achieved this by defining:

BlogEngine.user_class = "AuthEngine::User"

This way, he can easily ask for user data, even though it isn't stored in the same engine. The problem comes when we want to define relashionships between models

He can easily say that each blog post belongs to a user

has_one :user, :class_name => BlogEngine.user_class

But as far as i know he can't specify that each User has multiple posts since the User model is within the other engine

The consequence of this is that he can't do things like @user.posts, but instead has to do Post.find_all_by_user(@user)

Is there a more elegant way to deal with this? I also considered the possibility that each engine could simply generate the models inside the app, removing the encapsulation, but since the amount of models will grow quickly, i think this will make the app more of a mess, and not as much maintanable

Naps62
  • 960
  • 6
  • 17
  • 3
    Shouldn't do this. If they rely on each other you are breaking encapsulation and defeating the purpose of an engine. Merge the engines or have the model sharing happen in the main app instead. – Tanzeeb Khalili Jul 31 '12 at 09:39
  • The point of the engines here was mostly to separate the large amount of data that. I've been looking into a possible solution lately. Will post is once i have it working – Naps62 Aug 08 '12 at 02:43

2 Answers2

2

I think you should reopen user class inside blog_engine in order to define has_many :posts relation and it should be appropriate way.

Sandip Ransing
  • 7,583
  • 4
  • 37
  • 48
  • BlogPost and User are classes from two different engines. Would that still work? I think that might become messy due to load order, especially once i have multiple engines with similar issues – Naps62 Aug 08 '12 at 02:44
  • @Naps62 yes it will work .. and i guess you can specify load order in order to avoid issues. – Sandip Ransing Aug 09 '12 at 12:53
  • Ok i discussed this suggestion with my colleague. As for the specific question i asked here, this solution works, so i'll accept this answer. But we actually went with a different approach. We define Concerns inside our engines with the relations that are specific to that Engine. The Engine has a generator that creates the model inside the app (instead of containing it internally), and the model itself has only the includes for the required Concerns. Can anyone comment on this approach? – Naps62 Aug 09 '12 at 20:53
0

What about having a common models gem/engine with only the relationships as a dependency for your engines? This way you would have access to all relevant relationships in every engine.

Arthur Alkmim
  • 237
  • 1
  • 2
  • 10