`
yangzhihuan
  • 浏览: 168746 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

对于model是全部放在model下面,还是应该分开包来管理的疑问

阅读更多

ruby和rails的文章看了不少.不过都没有看到过讲述如何在rails下面,按模块来分类model的资料(比如像java那样用包来分类java文件,呵呵 ...我是一个java程序员).

我也试了一下把不同功能的model放在model(rails默认的)文件夹下面的子文件夹(模块,也是包),也是可以成功的,不过这样做的话,rails的约定高于配置就用不上了,因为要自己指定各个类的class.比如:

has_one :my_test,:class_name => 'Content::MyTest'

 这样.

我觉得这样比较不爽.

 

另外,

include Human

这样的代码在model和controller里面似乎并不起它就有的作用.比如:我有一Human::User的类,在controll入er里面加

include Human
,再使用
User.new

 这样的代码就会出错,提示也就是说找不到User类云云....

 

最后的感觉就是,rails的约定优于配置思想,确实是还来了好多方便,不过有时候未免不能随心所欲.

呵呵 ...... 也许是我强求了.

 

 

 

分享到:
评论
25 楼 liusong1111 2008-04-24  
pig345 写道
如果问题是:
liusong1111 写道

class A
end

module C
  module A
    class B
      # use class A
    end
  end
end



那么,考虑下:

ruby存在的时间比java更久,这么基础的问题(严重点说——缺陷)难道只有咱们碰到过?

或者是ruby社区长久以来对此一直视而不见???这、这ruby还能用么。。。




先放两句大话,呵呵,其实也是最近才找到解决方法,分享下:

class A
  def self.who?
    puts self
  end
end

module C
  module A
    class B
      def self.ask_A
        A.who? 
        ::A.who?
      end
    end
    def self.who?
      puts self
    end
  end
end

C::A::B.ask_A


irb里面实验下看看?


我前面的想法跟你所说没有冲突,我当时的思路还不清晰。
不是ruby的问题,而是直接依赖rails的自动加载机制不行,从理论上说,也无法解决。
假设你上面代码,class A定义在a.rb中,module C定义在c.rb中。c.rb没有显式require 'a.rb',我们假定事先加载了rails(或具体的active_support)。
module C中那行A.who? ,因为查找时先找到了module A,所以就用了它。而我本期望它会自动加载a.rb,使用class A的。由于提前找到const(module A)而短路了自动加载机制的const_missing,所以依赖这种加载的自动化不行。
解决方式有两种,一是手工require 'a.rb',并像你上面::A这样用。二是用model :a的声明。第二种方式我没有查看它的源码,大致推想它直接找到models目录的文件加载,跟第一种方法本质一样。

结论是:不是加载不到,而是不能自动加载到。
24 楼 blogbin 2008-03-18  
不过migrate无法支持按模块创建目录,所有的migratee都会放在一个db/migrate目录下。
习惯了java的package管理,感觉ruby or rails在这方面比较别扭。
23 楼 magicgod 2008-03-16  
2.0已经有了命名空间,例如:
ruby script/generate model Admin::User


这样将会生成
      create  app/models/admin
      create  test/unit/admin
      create  test/fixtures/admin
      create  app/models/admin/user.rb
      create  test/unit/admin/user_test.rb
      create  test/fixtures/admin_users.yml
      exists  db/migrate
      create  db/migrate/002_create_admin_users.rb


controller也可以。
22 楼 lllyq 2008-03-10  
我测试了一下,还有一个model不放在根下,要求跟control,helper的分层一致的理由
我用rspec,如果不一致,generate出来的代码还需要手工改,很麻烦,一致就没问题,例如都在users层(module)下,ruby script/generate rspec_controller users\user
21 楼 carlosbdw 2008-03-07  
希望rails能把controller分成两类:

1,主表维护
2,业务操作
20 楼 pig345 2008-03-07  
其实说严重点,这可以算ruby的一个语法陷阱,一般人很难会把所有使用类的地方都写上全路径,因此“写ruby第一要注意的就是:想尽一切办法避免重名”仍然是需要时刻提醒自己的。
19 楼 pig345 2008-03-07  
如果问题是:
liusong1111 写道

class A
end

module C
  module A
    class B
      # use class A
    end
  end
end



那么,考虑下:

ruby存在的时间比java更久,这么基础的问题(严重点说——缺陷)难道只有咱们碰到过?

或者是ruby社区长久以来对此一直视而不见???这、这ruby还能用么。。。




先放两句大话,呵呵,其实也是最近才找到解决方法,分享下:

class A
  def self.who?
    puts self
  end
end

module C
  module A
    class B
      def self.ask_A
        A.who?
        ::A.who?
      end
    end
    def self.who?
      puts self
    end
  end
end

C::A::B.ask_A


irb里面实验下看看?
18 楼 liusong1111 2008-03-06  
rails的自动加载机制源码在active_support的dependencies.rb,Waves框架的创始人说他的更好,抽成了一个叫autocode的gem: http://rubyforge.org/projects/autocode/

本质都是重写const_missing,难点是在重新加载文件之前需要卸载干净(remove_const)以前的const定义,否则在内存中相当于在老的const定义基础上合并了新的定义,会造成一些不可预期的问题 -- 比如重新加载的文件中对类A加了方法a,重定义了方法b,删了方法c,在运行过程中发现a,b都正确了,c居然还存在。由于const的定义本质是在执行过程中动态加入的,可以做到很灵活的添加const,没有机制标记某个const就是对应在哪个文件中创建的,所以需不需要以及如何标记哪些const可以被reload也是问题。rails于是约定了自动加载的类和其文件名/路径的对应关系(ruby语言本身没有这种强性要求)。

autocode的代码比rails清晰多了。
17 楼 seemoon 2008-03-06  
刚接触ruby没多少天,由于之前是用java的,觉得ruby在命名空间似乎处理得不如java那般明确,加上rails隐藏了很多类加载的机制和潜规则,所以如何来合理组织一个代码项目结构似乎成为了ror开发要解决的一大问题。不知道做过项目的同学能不能共享一下经验?
16 楼 liusong1111 2008-03-06  
pig345 写道
liusong1111 写道
按模块划分代码时,感觉rails的支持不是很完美。
如lgn21st所说,有时需要了解一些深层的原理,比如module和class在ruby中都是constant等。
module名和model名相同时也可能产生问题,比如有/controllers/admin/account_controller.rb和/models/admin.rb, 在account_controller里使用类似Admin.find(:all)时它会报错: Admin没有find方法。
这是因为在account_controller.rb在定义了Admin::AccountController,即module Admin和其下的class AccountController,而在admin.rb定义了class Admin,两个地方都定义了constant叫Admin,以哪个为准,取决于ruby查找constant的机制,ruby不同版本间也可能有差异,是不是还跟文件加载顺序相关我不清楚,对于这种情况我们用了rails2.0里已经去掉的model :admin声明,保证在controller里能正确加载使用model admin。--而不是直接找到它上层的module而绕过rails自动加载机制的const_missing。

写ruby第一要注意的就是“想尽一切办法避免重名”,不论是类/模块,还是方法/变量。。。
否则有你忙活的时候。


我们也在尽力避免重复和二义性情况的出现,能把类、模块、方法、变量的名字起到刻骨的好的程度,就是优秀设计的显著的外在表现,可世事难预料啊,呵呵~
ruby的module用于持有一些独立功能,它有两个职责:mixin和namespace,两者在原理上并没有明显的界限,前者重在功能动态增强,后者重在功能静态隔离,在实际使用中有可能重点使用职责之一。
ajoo老大前面的贴子提出当module作为namespace职责时表达形式不直观,我现在的问题是namespace的名字和类的名字冲突了,在java里package是小写,类名是大写,文件名/路径 与 package/class名字强制保持一致,ruby把namespace(module)和class都作为constant看待,rails重载const_missing实现自动加载,这是两者的不同,对于java来说这种问题就不容易出现。
namespace和class不应该重名吗?
以java的经验看,重名是可以理解的。以ruby实现的角度看,有潜在问题。
我现在也只好记着这个技术约束,注意父模块和同级的类重名的问题~

---
写ruby第一要注意的就是“想尽一切办法避免重名”,--- 我刚刚体会到你这句话的意思,对,深有体会,重名时执行的先后顺序决定最终结果,可能导致诡异的问题,动态性真是个双刃剑。我上面的问题跟这还有些区别:

class A
end

module C
  module A
    class B
      # use class A
    end
  end
end

15 楼 fiyuer 2008-03-06  
model比较多时可以放在多个目录下,只要在environment.rb下设置一下就可以直接拿过来用了

Rails::Initializer.run do |config|
  config.load_paths += Dir["#{RAILS_ROOT}/app/models/[a-z]*"]
end

[ "app/models" ].each do |path|
  Dir["#{RAILS_ROOT}/#{path}/**/*.rb"].each{|file|
    load file
  }
end
14 楼 lllyq 2008-03-06  
除了model,其他的controllers/services/helpers你都可以分层,就像java Package一样的,rails的classloader机制可以让你同一个module下不需require,所以只要分层一样用起来也很方便,这样也可以避免一些同名问题
13 楼 pig345 2008-03-06  
liusong1111 写道
按模块划分代码时,感觉rails的支持不是很完美。
如lgn21st所说,有时需要了解一些深层的原理,比如module和class在ruby中都是constant等。
module名和model名相同时也可能产生问题,比如有/controllers/admin/account_controller.rb和/models/admin.rb, 在account_controller里使用类似Admin.find(:all)时它会报错: Admin没有find方法。
这是因为在account_controller.rb在定义了Admin::AccountController,即module Admin和其下的class AccountController,而在admin.rb定义了class Admin,两个地方都定义了constant叫Admin,以哪个为准,取决于ruby查找constant的机制,ruby不同版本间也可能有差异,是不是还跟文件加载顺序相关我不清楚,对于这种情况我们用了rails2.0里已经去掉的model :admin声明,保证在controller里能正确加载使用model admin。--而不是直接找到它上层的module而绕过rails自动加载机制的const_missing。

写ruby第一要注意的就是“想尽一切办法避免重名”,不论是类/模块,还是方法/变量。。。
否则有你忙活的时候。
12 楼 yangzhihuan 2008-03-03  
如果model比较多,有100来个,那么全部放到models目录下,估计也是相当的壮观,找起来嘛,呵呵...更加是不用说了.
不过我暂时没有这么多model,所以暂时没有这个烦恼.

多谢大家热烈的讨论.....
11 楼 liusong1111 2008-03-03  
我们的controller组织在多层module/目录下,把model全部放在/models下,效果不错。
10 楼 liusong1111 2008-03-03  
按模块划分代码时,感觉rails的支持不是很完美。
如lgn21st所说,有时需要了解一些深层的原理,比如module和class在ruby中都是constant等。
module名和model名相同时也可能产生问题,比如有/controllers/admin/account_controller.rb和/models/admin.rb, 在account_controller里使用类似Admin.find(:all)时它会报错: Admin没有find方法。
这是因为在account_controller.rb在定义了Admin::AccountController,即module Admin和其下的class AccountController,而在admin.rb定义了class Admin,两个地方都定义了constant叫Admin,以哪个为准,取决于ruby查找constant的机制,ruby不同版本间也可能有差异,是不是还跟文件加载顺序相关我不清楚,对于这种情况我们用了rails2.0里已经去掉的model :admin声明,保证在controller里能正确加载使用model admin。--而不是直接找到它上层的module而绕过rails自动加载机制的const_missing。
9 楼 lllyq 2008-03-03  
我测试了,先include module再直接调用module下class是可以的,而且不同位置的同名module可以merge

不过activerecord这个问题估计难以解决,恐怕只能加class_name
8 楼 liusu 2008-03-02  
一直对Python,Ruby等语言的源码组织方法没有个好的办法。
因为做实际的项目从Java开始,习惯了Java的源码组织方法,呵呵
7 楼 lgn21st 2008-03-02  
在Ruby中,类名跟Java中的类名引用机制不同,Ruby的类名其实就是一个constant常量,模块名也是,跟在其他地方定义的常量一样,也就是说,你可以这样写
Book = Demo1::Book
@book = Book.new
不过我相信一旦习惯了ruby这种路子以后,就不会在觉得写Demo1::Book.new是很烦的事情了,因为看着直观哪.
6 楼 yangzhihuan 2008-03-02  
其实无他,我只是觉得
@book = Demo1::Book.new 

这样写有些长而已,我之前一直是搞java的,习惯了import一个包进来,然后就写一个类名.
不管怎么样,多谢lgn21st .

相关推荐

    JSONModel MVC demo

    JSONModel MVC demo是一个示例项目,它展示了如何在iOS应用中使用JSONModel框架来实现Model-View-Controller(MVC)设计模式。JSONModel是一个强大的库,用于将JSON数据自动映射到Objective-C或Swift的对象中,简化...

    客户管理-model

    客户管理-model

    填坑记录之Vue中v-model与:model区别

    初做vue项目中遇到这个问题,记录一下。 源代码: 打算做的表单验证功能。结果发现在验证的过程中username规则的第一条正确了却一直通过不...正确的做法应该将form标签中v-model改为 :model,这样在子组件中才可以获

    JSP的两种设计模式 Model1和Model2

    JSP的两种设计模式,即Model1和Model2,是Web开发中常见的架构模式,主要用于分离展示层、控制层和业务逻辑层,提高代码的可维护性和可扩展性。 **JSP Model1模式**是最基础的JSP开发模式,主要特点是将业务逻辑、...

    新闻管理系统model1模式

    总结来说,"新闻管理系统model1模式"是一个基于简化MVC架构的项目,它通过集中式处理来实现用户管理、新闻管理和安全控制。虽然在大型项目中可能不太适用,但对于初学者和小型项目,model1模式提供了一个快速开发和...

    model.h5 model.json

    在这个场景中,我们有两个关键文件:"model.h5" 和 "model.json",它们与人脸表情识别任务相关,这是一种利用计算机视觉和机器学习技术来理解人类情绪的先进技术。 `model.h5` 是一个Keras模型的权重和架构存储文件...

    Model View Presenter vs Model View Controller

    在软件开发领域,架构设计是至关重要的,因为它决定了应用程序的可维护性、可扩展...总的来说,理解并选择合适的UI设计模式对于构建高效、可维护的软件至关重要。开发者应根据项目特点和团队能力来决定采用MVP还是MVC。

    韩顺平的model2模式的新闻管理系统

    总结来说,“韩顺平的Model2模式的新闻管理系统”是一个采用经典设计模式构建的Web应用,通过合理的架构设计,实现了业务逻辑与用户界面的有效解耦,提高了系统的可维护性和可扩展性,对于学习和理解Web开发中的MVC...

    Model1和Model开发模式

    总的来说,Model1模式适用于小型、简单的Web应用,而Model2(MVC)模式更适合大型、复杂的项目,因为它提供了更好的可扩展性和可维护性。随着Web开发技术的不断发展,如Spring MVC、Struts等框架的出现,MVC模式得到...

    Modeltest 使用说明

    下面是 Modeltest 的使用说明和相关知识点: 一、Modeltest 概述 * Modeltest 是一个计算机程序,由 David Posada 和 Keith A Crondall 创建 * 主要用于计算 DNA 演化的最佳模型,使用 Maximum Likelihood(ML)...

    QTreeView 使用自定义Model

    本篇文章将深入探讨如何使用QTreeView,并结合自定义Model来实现更灵活的数据展现。 首先,理解QTreeView的工作原理至关重要。QTreeView本身并不存储数据,它只是视图部分,负责呈现数据。数据由Model提供,Model是...

    C#自动生成MODEL

    例如,对于一个数据库表,自动生成的MODEL类会包含该表的所有字段作为类的属性,并且可能还包括一些基本的CRUD(Create, Read, Update, Delete)操作。 在描述中提到的“部分数据存储数据结构”,这可能指的是特定...

    C#自动生成Model工具源码

    对于开发者来说,了解这个工具的工作流程和使用方式是非常重要的。它可以帮助快速构建数据访问层,使得开发者可以更专注于业务逻辑的实现,而不是重复的代码编写。此外,这样的工具通常具有一定的定制性,可以通过...

    用Model-Editor建立Pspice模型

    具体来说,用户需要根据数据手册提供的数据点,在Model Editor中设定参数,Model Editor会帮助用户通过数值分析法计算出符合描点设定的参数值。这些参数值之后会被用于定义元件模型的行为。 此外,Model Editor还...

    tp5快速生成model文件.zip

    下面我们将深入探讨TP5中的Model及其快速生成的方法。 在TP5中,Model类主要负责与数据库的交互,包括数据的增删查改(CRUD)操作。开发者通常会为每个数据库表创建一个对应的Model类,这样可以使代码更加结构化和...

    swift语言model的使用

    Swift语言中的Model是MVC(Model-View-Controller)设计模式的一个重要组成部分,它负责存储和管理应用程序的数据。在iOS开发中,Model层通常包含了业务逻辑、数据处理以及与服务器或本地数据库的交互。本项目以`...

    iOS一键生成model

    在iOS开发中,Model层是应用程序的重要组成部分,它负责存储和管理数据。"iOS一键生成model"的主题意味着我们要探讨一种能够快速、自动化地创建数据模型类的方法,这在处理大量结构化数据时尤为有用。传统的做法是...

    vosk中文model资源,

    总的来说,Vosk中文模型为开发者提供了一个强大且灵活的工具,用于实现高效、可靠的中文语音识别功能,无论是在智能家居、车载导航还是语音助手等场景,都能发挥重要作用。通过持续的更新和优化,我们可以期待Vosk在...

    Qt Model/View 学习笔记

    Qt 4推出了一组新的item view类,它们使用model/view结构来管理数据与表示层的关系。这种结构带来的 功能上的分离给了开发人员更大的弹性来定制数据项的表示,它也提供一个标准的model接口,使得更多的 数据源可以被...

Global site tag (gtag.js) - Google Analytics