什么是Ruby on Rails ORM的外行人的术语? 请解释
我在Ruby on Rails中无法理解ORM。 据我所知,表/列和对象/属性之间存在1:1的关系。 所以每条记录都是一个对象。 究竟什么是模型? 我知道它映射到一张桌子。
我真正追求的是对上述内容的更深入理解。 预先感谢您的帮助
我是一名从PHP到Ruby on Rails的Web开发人员。
“根据我的理解,表/列和对象/属性之间存在1:1的关系。所以每条记录都是一个对象。”
这不完全正确,除非你非常宽松地使用术语“对象”。 表由类建模,而表记录由这些类的实例建模。
假设您有一个clients
表,其中包含列id
(autonum)和name
(varchar)。 假设它只有一条记录,id = 1,名字=“Ford”。 然后:
- DB表
clients
将映射到模型类Client
。 - 记录将映射到模型实例 ,这意味着您必须创建对象并将其分配给变量才能使用记录。 最常见的方法是做
ford = Client.find(1)
- 表的两列将映射到
ford
变量上的方法。 你可以做ford.id
,你会得到1.你可以做ford.name
,你会得到字符串“福特”。 您还可以通过执行ford.name = "Chevrolet"
来更改客户端的名称,然后通过执行ford.save在数据库上提交更改。
“还究竟什么是模型?我知道它映射到一个表”
模型只是具有许多非常有用的方法来操作数据库的类。 这里有些例子:
- validation :除了典型的数据库驱动validation(“此字段不能为空”),您可以在ruby中实现许多复杂的validation(“此字段必须是有效的电子邮件”是最典型的validation)。 在模型实例上调用“save”之前运行validation。
- 关系 :外键也可以映射到模型上。 例如,如果您有一个
brands
表(及其相应的Brand
型号)通过外键与您的福特客户关联,您可以执行ford.brands
,您将得到一个对象数组,表示品牌表上的所有记录client_id = 1。 - 查询 :模型允许您在ruby中创建查询,并将它们自己转换为SQL。 大多数人都喜欢这个function。
这只是一些例子。 活动记录提供了更多function,例如翻译,查询范围或支持单表inheritance。
最后但并非最不重要的是,您可以将自己的方法添加到这些类中。
模型是不编写“spaguetti代码”的好方法,因为您不得不按function分离代码。
- 模型处理数据库交互和业务逻辑
- 视图处理html呈现和用户交互
- 控制器将模型与视图连接
Rails中的ORM是Martin Fowler的企业应用程序架构模式书中的Active Record模式的实现。 因此,Rails ORM框架被命名为ActiveRecord。
基本思想是将数据库表包装到类中,并且对象的实例对应于该表中的单个行。 因此,创建新实例会向表中添加一行,更新对象会更新行等。包装类会为表中的每个列实现属性。 在Rails的ActiveRecord中,这些属性可以使用基于数据库模式的Ruby元编程自动获得。 如果需要引入其他逻辑,可以根据需要覆盖这些属性。 您还可以添加所谓的虚拟属性 ,这些属性在基础数据库表中没有对应的列。
Rails是一个模型 – 视图 – 控制器 (MVC)框架,因此Rails模型是MVC中的M. 它不仅是上面描述的ActiveRecord包装类,还包含业务逻辑,包括由ActiveRecord的Validation模块实现的validation逻辑。
进一步阅读
- Rails数据库迁移指南
- Rails Active Record Validations和Callbacks指南
- 活动记录协会指南
- Active Record Query Interface指南
- Active Record API文档
模型 :域对象,如User
, Account
或Status
。 数据库后端不一定支持模型,例如Status
可以只是一个简单的静态类型枚举。
ActiveRecord :
提供用于查询数据库表的动态方法。 数据库表被定义为inheritanceActiveRecord类的类(伪PHP示例):
class User extends ActiveRecord {} //find a record by name, and returns an instance of `User` $record = User::find_by_name("Imran"); echo $record->name; //prints "Imran" //there are a lot more dynamic methods for quering
通过创建ActiveRecordinheritance类的新实例来创建新记录:
class Account extends ActiveRecord {} $account = new Account(); $account->name = "Bank Account"; $account->save();
这里有两个部分:ORM和Rails的MVC模式。 ORM是“对象 – 关系映射”的缩写,它完全符合它所说的:它将数据库中的表映射到可以使用的对象。
MVC是“模型 – 视图 – 控制器”的缩写,模型描述了Rails如何将您的域行为和对象表示转换为有用的页面。 MVC模式分为三个块:
-
模型包含域中对象所代表的内容的定义,以及它与其他模型的关系。 它还描述了对象映射中的字段和关系如何映射到后备存储(例如数据库)。 请注意,本身没有任何关于模型的规定,您必须使用特定的ORM(甚至是ORM)。
-
控制器指定模型应如何相互交互以产生响应用户请求的有用结果。
-
视图获取控制器创建的结果并以所需方式呈现它们。 (当你进入你的观点时,你应该知道正在渲染什么,并且应该发生很少的行为。)
维基百科的定义 :
计算机软件中的对象关系映射(ORM,O / RM和O / R映射)是用于在关系数据库和面向对象的编程语言中的不兼容类型系统之间转换数据的编程技术。 这实际上创建了可以在编程语言中使用的“虚拟对象数据库”。
从PHP视图来看,它将采用以下方式(通过示例)
- 连接到数据库并从posts表中获取一些行。
- 将该行转换为具有表列中属性的对象。
- 如果post在评论表中有评论,你也可以做post.comments,你也可以将评论作为一个对象数组。
您可以定义表之间的关系,例如:posthas_many评论,评论属于post等等。
因此,基本上您不使用数据库行,而是将这些行及其关系转换为具有组合或inheritance关系的对象。
用外行人的话说。
- Rails 模型是数据库中表的代理。 这些模型恰好是Ruby类。
- 这些类的对象是表中行的代理,该模型是代理的表。
- 最后,这些对象的属性是该特定行的列数据的代理。
上面实际上是Rails ActiveRecord ORM。
1:1不太正确,因为存在物体关系阻抗不匹配 。