Active Record – Rails 中的对象关系映射
Active Record 将类连接到关系数据库表,为应用程序建立几乎零配置的持久层。该库提供了一个基类,当子类化时,会在新类和数据库中现有的表之间建立映射。在应用程序的上下文中,这些类通常称为模型。模型还可以连接到其他模型;这是通过定义关联来完成的。
Active Record 在很大程度上依赖于命名,因为它使用类和关联名称来建立各个数据库表和外键列之间的映射。虽然这些映射可以显式定义,但建议遵循命名约定,尤其是在开始使用该库时。
您可以在Active Record 基础指南中阅读有关 Active Record 的更多信息。
以下是对一些主要功能的简要概述
-
在类和表、属性和列之间进行自动映射。
class Product < ActiveRecord::Base end
Product 类自动映射到名为“products”的表,该表可能如下所示
CREATE TABLE products ( id bigint NOT NULL auto_increment, name varchar(255), PRIMARY KEY (id) );
这也将定义以下访问器:
Product#name
和Product#name=(new_name)
。 -
关联
由简单的类方法定义的对象之间。class Firm < ActiveRecord::Base has_many :clients has_one :account belongs_to :conglomerate end
-
聚合
值对象。class Account < ActiveRecord::Base composed_of :balance, class_name: 'Money', mapping: %w(balance amount) composed_of :address, mapping: [%w(address_street street), %w(address_city city)] end
-
对于新对象或现有对象,验证规则可能有所不同。
class Account < ActiveRecord::Base validates :subdomain, :name, :email_address, :password, presence: true validates :subdomain, uniqueness: true validates :terms_of_service, acceptance: true, on: :create validates :password, :email_address, confirmation: true, on: :create end
-
回调
可用于整个生命周期(实例化、保存、销毁、验证等)。class Person < ActiveRecord::Base before_destroy :invalidate_payment_plan # the `invalidate_payment_plan` method gets called just before Person#destroy end
-
继承
层次结构。class Company < ActiveRecord::Base; end class Firm < Company; end class Client < Company; end class PriorityClient < Client; end
-
事务
.# Database transaction Account.transaction do david.withdrawal(100) mary.deposit(100) end
-
对列、关联和聚合的反映。
reflection = Firm.reflect_on_association(:clients) reflection.klass # => Client (class) Firm.columns # Returns an array of column descriptors for the firms table
-
通过简单的适配器进行数据库抽象。
# connect to SQLite3 ActiveRecord::Base.establish_connection(adapter: 'sqlite3', database: 'dbfile.sqlite3') # connect to MySQL with authentication ActiveRecord::Base.establish_connection( adapter: 'mysql2', host: 'localhost', username: 'me', password: 'secret', database: 'activerecord' )
了解更多信息并阅读有关对 MySQL、PostgreSQL 和 SQLite3 的内置支持。
-
ActiveRecord::Base.logger = ActiveSupport::Logger.new(STDOUT) ActiveRecord::Base.logger = Log4r::Logger.new('Application Log')
-
使用迁移进行与数据库无关的架构管理。
class AddSystemSettings < ActiveRecord::Migration[7.1] def up create_table :system_settings do |t| t.string :name t.string :label t.text :value t.string :type t.integer :position end SystemSetting.create name: 'notice', label: 'Use notice?', value: 1 end def down drop_table :system_settings end end
理念
Active Record 是对象关系映射 (ORM) 的实现,由 Martin Fowler 描述的同名 模式
“一个对象,它包装在数据库表或视图中的行中,封装了数据库访问,并在该数据上添加了领域逻辑。”
Active Record 尝试提供一个连贯的包装器,作为对象关系映射不便的一种解决方案。此映射的主要指令是最大程度地减少构建真实世界领域模型所需的代码量。这可以通过依赖许多约定来实现,这些约定使 Active Record 能够轻松地从最少的明确指导中推断出复杂的关系和结构。
惯例优于配置
-
没有 XML 文件!
-
大量的反射和运行时扩展
-
魔术本质上不是一个坏词
承认数据库
-
允许您在特殊情况下和性能方面使用 SQL
-
不会尝试复制或替换数据定义
下载和安装
可以使用 RubyGems 安装最新版本的 Active Record
$ gem install activerecord
可以从 GitHub 上的 Rails 项目下载源代码
许可证
Active Record 在 MIT 许可证下发布
支持
API 文档位于
Ruby on Rails 项目的错误报告可在此处提交
功能请求应在此处 rails-core 邮件列表中讨论
- 模块 ActiveRecord::Aggregations
- 模块 ActiveRecord::Associations
- 模块 ActiveRecord::AttributeAssignment
- 模块 ActiveRecord::AttributeMethods
- 模块 ActiveRecord::Attributes
- 模块 ActiveRecord::AutosaveAssociation
- 模块 ActiveRecord::Batches
- 模块 ActiveRecord::Calculations
- 模块 ActiveRecord::Callbacks
- 模块 ActiveRecord::Coders
- 模块 ActiveRecord::ConnectionAdapters
- 模块 ActiveRecord::ConnectionHandling
- 模块 ActiveRecord::Core
- 模块 ActiveRecord::CounterCache
- 模块 ActiveRecord::DelegatedType
- 模块 ActiveRecord::DynamicMatchers
- 模块 ActiveRecord::Encryption
- 模块 ActiveRecord::Enum
- 模块 ActiveRecord::Explain
- 模块 ActiveRecord::FinderMethods
- 模块 ActiveRecord::Inheritance
- 模块 ActiveRecord::Integration
- 模块 ActiveRecord::Locking
- 模块 ActiveRecord::Marshalling
- 模块 ActiveRecord::MessagePack
- 模块 ActiveRecord::Middleware
- 模块 ActiveRecord::ModelSchema
- 模块 ActiveRecord::NestedAttributes
- 模块 ActiveRecord::NoTouching
- 模块 ActiveRecord::Normalization
- 模块 ActiveRecord::Persistence
- 模块 ActiveRecord::QueryLogs
- 模块 ActiveRecord::QueryMethods
- 模块 ActiveRecord::Querying
- 模块 ActiveRecord::ReadonlyAttributes
- 模块 ActiveRecord::Reflection
- 模块 ActiveRecord::Sanitization
- 模块 ActiveRecord::Scoping
- 模块 ActiveRecord::SecurePassword
- 模块 ActiveRecord::SecureToken
- 模块 ActiveRecord::Serialization
- 模块 ActiveRecord::SignedId
- 模块 ActiveRecord::SpawnMethods
- 模块 ActiveRecord::Store
- 模块 ActiveRecord::Suppressor
- 模块 ActiveRecord::Tasks
- 模块 ActiveRecord::TestFixtures
- 模块 ActiveRecord::Timestamp
- 模块 ActiveRecord::TokenFor
- 模块 ActiveRecord::Transactions
- 模块 ActiveRecord::Translation
- 模块 ActiveRecord::Type
- 模块 ActiveRecord::VERSION
- 模块 ActiveRecord::Validations
- 类 ActiveRecord::ActiveRecordError
- 类 ActiveRecord::AdapterError
- 类 ActiveRecord::AdapterNotFound
- 类 ActiveRecord::AdapterNotSpecified
- 类 ActiveRecord::AdapterTimeout
- 类 ActiveRecord::AssociationTypeMismatch
- 类 ActiveRecord::AsynchronousQueryInsideTransactionError
- 类 ActiveRecord::AttributeAssignmentError
- 类 ActiveRecord::Base
- 类 ActiveRecord::ConfigurationError
- 类 ActiveRecord::ConnectionFailed
- 类 ActiveRecord::ConnectionNotEstablished
- 类 ActiveRecord::ConnectionTimeoutError
- 类 ActiveRecord::DangerousAttributeError
- 类 ActiveRecord::DatabaseAlreadyExists
- 类 ActiveRecord::DatabaseConfigurations
- 类 ActiveRecord::DatabaseConnectionError
- 类 ActiveRecord::Deadlocked
- 类 ActiveRecord::DestroyAssociationAsyncError
- 类 ActiveRecord::DestroyAssociationAsyncJob
- 类 ActiveRecord::EagerLoadPolymorphicError
- 类 ActiveRecord::EnvironmentMismatchError
- 类 ActiveRecord::ExclusiveConnectionTimeoutError
- 类 ActiveRecord::FixtureSet
- 类 ActiveRecord::FutureResult
- 类 ActiveRecord::ImmutableRelation
- 类 ActiveRecord::InvalidForeignKey
- 类 ActiveRecord::IrreversibleMigration
- 类 ActiveRecord::IrreversibleOrderError
- 类 ActiveRecord::LockWaitTimeout
- 类 ActiveRecord::LogSubscriber
- 类 ActiveRecord::Migration
- 类 ActiveRecord::MigrationContext
- 类 ActiveRecord::MismatchedForeignKey
- 类 ActiveRecord::MultiparameterAssignmentErrors
- 类 ActiveRecord::NoDatabaseError
- 类 ActiveRecord::NotNullViolation
- CLASS ActiveRecord::PreparedStatementCacheExpired
- CLASS ActiveRecord::PreparedStatementInvalid
- CLASS ActiveRecord::Promise
- CLASS ActiveRecord::QueryAborted
- CLASS ActiveRecord::QueryCache
- CLASS ActiveRecord::QueryCanceled
- CLASS ActiveRecord::RangeError
- CLASS ActiveRecord::ReadOnlyError
- CLASS ActiveRecord::ReadOnlyRecord
- CLASS ActiveRecord::ReadonlyAttributeError
- CLASS ActiveRecord::RecordInvalid
- CLASS ActiveRecord::RecordNotDestroyed
- CLASS ActiveRecord::RecordNotFound
- CLASS ActiveRecord::RecordNotSaved
- CLASS ActiveRecord::RecordNotUnique
- CLASS ActiveRecord::Relation
- CLASS ActiveRecord::Result
- CLASS ActiveRecord::Rollback
- CLASS ActiveRecord::SQLWarning
- CLASS ActiveRecord::Schema
- CLASS ActiveRecord::SerializationFailure
- CLASS ActiveRecord::SerializationTypeMismatch
- CLASS ActiveRecord::SoleRecordExceeded
- CLASS ActiveRecord::StaleObjectError
- CLASS ActiveRecord::StatementCache
- CLASS ActiveRecord::StatementInvalid
- CLASS ActiveRecord::StatementTimeout
- CLASS ActiveRecord::StrictLoadingViolationError
- CLASS ActiveRecord::SubclassNotFound
- CLASS ActiveRecord::TableNotSpecified
- 类 ActiveRecord::TransactionIsolationError
- 类 ActiveRecord::TransactionRollbackError
- 类 ActiveRecord::UnknownAttributeError
- 类 ActiveRecord::UnknownAttributeReference
- 类 ActiveRecord::UnknownPrimaryKey
- 类 ActiveRecord::ValueTooLong
- 类 ActiveRecord::WrappedDatabaseException
- D
- E
- G
- L
- M
- S
- U
- V
常量
MigrationProxy | = | Struct.new(:name, :version, :filename, :scope) do def initialize(name, version, filename, scope) super @migration = nil end def basename File.basename(filename) end delegate :migrate, :announce, :write, :disable_ddl_transaction, to: :migration private def migration @migration ||= load_migration end def load_migration Object.send(:remove_const, name) rescue nil load(File.expand_path(filename)) name.constantize.new(name, version) end end |
|
||
Point | = | Struct.new(:x, :y) |
UnknownAttributeError | = | ActiveModel::UnknownAttributeError |
Active Model UnknownAttributeError当通过批量赋值提供未知属性时引发。
|
属性
[RW] | application_record_class | |
[RW] | async_query_executor | |
[RW] | before_committed_on_all_records | |
[RW] | belongs_to_required_validates_foreign_key | |
[RW] | commit_transaction_on_non_local_return | |
[R] | db_warnings_action | |
[RW] | db_warnings_ignore | |
[R] | default_timezone | |
[RW] | disable_prepared_statements | |
[RW] | index_nested_attribute_errors | |
[RW] | lazily_load_schema_cache | |
[RW] | maintain_test_schema | |
[RW] | query_transformers | |
[RW] | raise_on_assign_to_attr_readonly | |
[RW] | reading_role | |
[RW] | run_after_transaction_callbacks_in_order_defined | |
[RW] | schema_cache_ignored_tables | |
[RW] | writing_role |
类公共方法
db_warnings_action=(action) 链接
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 211 def self.db_warnings_action=(action) @db_warnings_action = case action when :ignore nil when :log ->(warning) do warning_message = "[#{warning.class}] #{warning.message}" warning_message += " (#{warning.code})" if warning.code ActiveRecord::Base.logger.warn(warning_message) end when :raise ->(warning) { raise warning } when :report ->(warning) { Rails.error.report(warning, handled: true) } when Proc action else raise ArgumentError, "db_warnings_action must be one of :ignore, :log, :raise, :report, or a custom proc." end end
default_timezone=(default_timezone) 链接
确定从数据库中提取日期和时间时使用 Time.utc(使用 :utc)还是 Time.local(使用 :local)。默认设置为 :utc。
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 196 def self.default_timezone=(default_timezone) unless %i(local utc).include?(default_timezone) raise ArgumentError, "default_timezone must be either :utc (default) or :local." end @default_timezone = default_timezone end
disconnect_all!() 链接
显式关闭所有池中的所有数据库连接。
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 476 def self.disconnect_all! ConnectionAdapters::PoolConfig.disconnect_all! end
eager_load!() 链接
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 465 def self.eager_load! super ActiveRecord::Locking.eager_load! ActiveRecord::Scoping.eager_load! ActiveRecord::Associations.eager_load! ActiveRecord::AttributeMethods.eager_load! ActiveRecord::ConnectionAdapters.eager_load! ActiveRecord::Encryption.eager_load! end
gem_version() 链接
返回当前加载的 ActiveRecord 版本,格式为 Gem::Version
。
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record/gem_version.rb, line 5 def self.gem_version Gem::Version.new VERSION::STRING end
global_executor_concurrency=(global_executor_concurrency) 链接
设置 global_executor_concurrency
。此配置值只能与全局线程池异步查询执行器一起使用。
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 278 def self.global_executor_concurrency=(global_executor_concurrency) if self.async_query_executor.nil? || self.async_query_executor == :multi_thread_pool raise ArgumentError, "`global_executor_concurrency` cannot be set when using the executor is nil or set to multi_thead_pool. For multiple thread pools, please set the concurrency in your database configuration." end @global_executor_concurrency = global_executor_concurrency end
legacy_connection_handling=(_) 链接
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 245 def self.legacy_connection_handling=(_) raise ArgumentError, <<~MSG.squish The `legacy_connection_handling` setter was deprecated in 7.0 and removed in 7.1, but is still defined in your configuration. Please remove this call as it no longer has any effect." MSG end
marshalling_format_version() 链接
源代码: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 457 def self.marshalling_format_version Marshalling.format_version end