两个rails应用程序共享模型文件夹

我有两个在同一个数据库上运行的rails应用程序,一个运行客户端,另一个提供管理界面。

这两个应用程序都具有完全相同的模型,除了少量的差异。 我很厌烦将模型中的绝大多数更改复制到两个应用程序。

两个应用程序使用相同模型信息的一种方法是将模型文件夹从一个应用程序符号链接到另一个应用程序,但由于代码中的一些差异(例如客户端上的额外validation),我无法做到这一点。

有没有一种简单的方法可以解决差异所以我可以将公共代码保存在一个地方?

为什么不以OOP方式进行,例如创建一个单独的基类(在一个单独的目录中),然后在两个项目中inheritance它,因此差异在inheritance的类中。

所以你有了

class BaseModel < ActiveRecord::Base 

在“common”子目录中,然后你就有了

 class AdminBaseModel < Common::BaseModel 

在管理项目和

 class UserBaseModel < Common::BaseModel 

你可能需要

 set_table_name "basemodel" 

所以Rails知道要打开哪个表。

svn:externals或git子模块绝对是这种情况的出路。

当然,您希望能够在两个应用程序中测试它们,因此您也应该共享您的模型测试或规格。 但请记住,模型通常依赖于插件,因此您也希望共享插件文件夹。 你可能想要相同的gem和相同版本的Rails,所以你最好的选择是分享所有的供应商。 哦,有时你的lib中的代码会修改你的模型,所以你要分享它。 哦,并确保在环境文件中共享任何自定义配置。

并且您希望设置一个持续集成服务器来在两个应用程序上运行测试套件,以防主应用程序中模型层的更改破坏您的其他应用程序。

但我的意思是,一旦完成所有这些,svn:externals或git子模块绝对是这种情况的方法。

更新 (几年后)

Rails Engines可能是目前在多个应用程序之间可靠地共享模型代码的最佳选择。 它们可以被gem化并包含在每个应用程序的Gemfile中。

我处理一个类似问题的项目,我们使用svn:externals在两个应用程序之间共享模型代码。

基本上,你在一个svn项目中有模型diretory,并在另一个项目中使用外部来共享代码。 您可以在任一项目中编辑代码,并在其他项目中运行svn up时更新。

就Rails和构建脚本而言,两个模型目录是完全独立的。

是,对模板目录进行符号链接,然后为每个实例的environment.rb添加一个环境变量。 然后,您的模型可以知道哪个实例正在使用它并包含其他validation或不包含。

在environment.rb中:

 APP_INSTANCE = "app1" 

在model.rb中

 validates_length_of :name, :within => 3..100, :if => :is_app_one? def is_app_one? APP_INSTANCE == "app1" end 

您可以将一个rails项目视为gem,然后通过将模型路径添加到其加载路径,您可以在其他rails项目中使用它。

这是一个例子,我想你可以得到它,虽然它是用中文写的。 http://mvj3.github.com/2011/09/13/multiple_rails_apps_sharing_models_folder/

只是好奇 – 为什么没有一个应用程序有两种模式?

我有一个应用程序看起来像十几个不同的应用程序之一,品牌不同,具有不同的function,具体取决于您进入的URL和您登录的人。 我的用户有角色,我向ActiveRecord :: Base添加了一个方法,为您提供当前用户。 因此,我可以做的事情:

 MAX_VOLUME = current_user.admin? ? 11 : 10 validates_inclusion_of :volume, :in => 0..MAX_VOLUME # Admins can go to 11! 

在视图中,这样的东西:

 <%= render :partial => common_tabs %> <%= render :partial => admin_tabs if @current_user.admin? %> 

为什么不使用组合而不是inheritance?

我有一个类似的问题:管理员应用程序和公共应用程序,具有相同的数据库,并且在一些应用程序或其他应用程序的某些模型上只有一些特定方法。

我目前正在考虑我可以创建一个包含许多模块的公共场所,我会将其放在我的方法中。 然后,当我需要时,我会在每个应用程序(模型,控制器,帮助器……)中包含我需要的模块。 这个地方可以在lib目录中(使用git子模块或svm外部更新)或在gem中(使用Bundler或类似工具更新)。

你怎么看待这件事 ?