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[8.0] 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 是对 Martin Fowler 描述的同名对象关系映射 (ORM) 模式 的实现
“一个封装数据库表或视图中的行、封装数据库访问并为该数据添加领域逻辑的对象。”
Active Record 试图提供一个连贯的包装器,作为对对象关系映射的不便的解决方案。这种映射的主要指导原则是将构建真实世界领域模型所需的代码量降到最低。这可以通过依赖一些约定来实现,这些约定使 Active Record 能够从最少的显式方向推断出复杂的关系和结构。
约定优于配置
-
没有 XML 文件!
-
大量的反射和运行时扩展
-
魔法本身并不是一个坏词
承认数据库
-
允许您在特殊情况下和性能方面降级到 SQL
-
不会尝试复制或替换数据定义
下载和安装
可以使用 RubyGems 安装最新版本的 Active Record
$ gem install activerecord
源代码可以作为 Rails 项目的一部分从 GitHub 下载
许可证
Active Record 在 MIT 许可下发布
支持
API 文档位于
Ruby on Rails 项目的错误报告可以在这里提交
功能请求应该在以下位置的 rails-core 邮件列表中讨论
验证错误类,用于包装关联记录的错误,支持 index_errors。
- 模块 ActiveRecord::Aggregations
- 模块 ActiveRecord::Assertions
- 模块 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::ConnectionNotDefined
- 类 ActiveRecord::ConnectionNotEstablished
- 类 ActiveRecord::ConnectionTimeoutError
- 类 ActiveRecord::DangerousAttributeError
- 类 ActiveRecord::DatabaseAlreadyExists
- 类 ActiveRecord::DatabaseConfigurations
- 类 ActiveRecord::DatabaseConnectionError
- 类 ActiveRecord::DatabaseVersionError
- 类 ActiveRecord::Deadlocked
- 类 ActiveRecord::DestroyAssociationAsyncError
- 类 ActiveRecord::DestroyAssociationAsyncJob
- 类 ActiveRecord::EagerLoadPolymorphicError
- 类 ActiveRecord::EnvironmentMismatchError
- 类 ActiveRecord::ExclusiveConnectionTimeoutError
- 类 ActiveRecord::FixtureSet
- 类 ActiveRecord::FutureResult
- 类 ActiveRecord::InvalidForeignKey
- 类 ActiveRecord::IrreversibleMigration
- 类 ActiveRecord::IrreversibleOrderError
- 类 ActiveRecord::LockWaitTimeout
- 类 ActiveRecord::LogSubscriber
- 类 ActiveRecord::Migration
- 类 ActiveRecord::MigrationContext
- 类 ActiveRecord::MismatchedForeignKey
- 类 ActiveRecord::MultiparameterAssignmentErrors
- 类 ActiveRecord::NoDatabaseError
- 类 ActiveRecord::NotNullViolation
- 类 ActiveRecord::PreparedStatementCacheExpired
- 类 ActiveRecord::PreparedStatementInvalid
- 类 ActiveRecord::Promise
- 类 ActiveRecord::QueryAborted
- 类 ActiveRecord::QueryCache
- 类 ActiveRecord::QueryCanceled
- 类 ActiveRecord::RangeError
- 类 ActiveRecord::ReadOnlyError
- 类 ActiveRecord::ReadOnlyRecord
- 类 ActiveRecord::ReadonlyAttributeError
- 类 ActiveRecord::RecordInvalid
- 类 ActiveRecord::RecordNotDestroyed
- 类 ActiveRecord::RecordNotFound
- 类 ActiveRecord::RecordNotSaved
- 类 ActiveRecord::RecordNotUnique
- 类 ActiveRecord::Relation
- 类 ActiveRecord::Result
- 类 ActiveRecord::Rollback
- 类 ActiveRecord::SQLWarning
- 类 ActiveRecord::Schema
- 类 ActiveRecord::SerializationFailure
- 类 ActiveRecord::SerializationTypeMismatch
- 类 ActiveRecord::SoleRecordExceeded
- 类 ActiveRecord::StaleObjectError
- 类 ActiveRecord::StatementCache
- 类 ActiveRecord::StatementInvalid
- 类 ActiveRecord::StatementTimeout
- 类 ActiveRecord::StrictLoadingViolationError
- 类 ActiveRecord::SubclassNotFound
- 类 ActiveRecord::TableNotSpecified
- 类 ActiveRecord::Transaction
- 类 ActiveRecord::TransactionIsolationError
- 类 ActiveRecord::TransactionRollbackError
- 类 ActiveRecord::UnknownAttributeError
- 类 ActiveRecord::UnknownAttributeReference
- 类 ActiveRecord::UnknownPrimaryKey
- 类 ActiveRecord::UnmodifiableRelation
- 类 ActiveRecord::ValueTooLong
- 类 ActiveRecord::WrappedDatabaseException
- A
- D
- E
- G
- L
- M
- P
- Q
- R
- S
- T
- U
- V
- Y
常量
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 |
|
||
点 | = | Struct.new(:x, :y) |
UnknownAttributeError | = | ActiveModel::UnknownAttributeError |
Active Model UnknownAttributeError当通过批量赋值提供未知属性时引发。
|
属性
[RW] | application_record_class | |
[RW] | before_committed_on_all_records | |
[RW] | belongs_to_required_validates_foreign_key | |
[RW] | database_cli | |
[R] | default_timezone | |
[RW] | disable_prepared_statements | |
[RW] | index_nested_attribute_errors | |
[RW] | maintain_test_schema | |
[R] | permanent_connection_checkout | |
[RW] | query_transformers | |
[RW] | raise_on_assign_to_attr_readonly | |
[RW] | reading_role | |
[RW] | run_after_transaction_callbacks_in_order_defined | |
[RW] | writing_role |
类公共方法
action_on_strict_loading_violation 链接
将应用程序设置为在关联违反严格加载时记录或引发异常。默认为 :raise。
来源: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 361 singleton_class.attr_accessor :action_on_strict_loading_violation
after_all_transactions_commit(&block) 链接
注册一个块,该块将在所有当前事务提交后被调用。
如果没有当前打开的事务,则立即调用该块。
如果存在多个嵌套事务,则在最外层事务提交后调用该块。
如果当前打开的任何事务回滚,则永远不会调用该块。
如果在多个数据库中打开了多个事务,则在所有事务提交后调用该块。但是请注意,跨两个不同数据库嵌套事务是一种分片反模式,会带来许多问题。
来源: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 527 def self.after_all_transactions_commit(&block) open_transactions = all_open_transactions if open_transactions.empty? yield elsif open_transactions.size == 1 open_transactions.first.after_commit(&block) else count = open_transactions.size callback = -> do count -= 1 block.call if count.zero? end open_transactions.each do |t| t.after_commit(&callback) end open_transactions = nil # rubocop:disable Lint/UselessAssignment avoid holding it in the closure end end
async_query_executor 链接
为应用程序设置 async_query_executor
。默认情况下,线程池执行器设置为 nil
,这将不会在后台运行查询。应用程序必须配置线程池执行器才能使用此功能。选项是
* nil - Does not initialize a thread pool executor. Any async calls will be
run in the foreground.
* :global_thread_pool - Initializes a single +Concurrent::ThreadPoolExecutor+
that uses the +async_query_concurrency+ for the +max_threads+ value.
* :multi_thread_pool - Initializes a +Concurrent::ThreadPoolExecutor+ for each
database connection. The initializer values are defined in the configuration hash.
来源: 显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 283 singleton_class.attr_accessor :async_query_executor
db_warnings_action 链接
当数据库查询产生警告时要采取的操作。必须是 :ignore、:log、:raise、:report 中的一种,或自定义 proc。默认值为 :ignore。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 233 singleton_class.attr_reader :db_warnings_action
db_warnings_action=(action) 链接
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 235 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
db_warnings_ignore 链接
指定数据库警告的白名单。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 262 singleton_class.attr_accessor :db_warnings_ignore
default_timezone=(default_timezone) 链接
决定从数据库中提取日期和时间时,是否使用 Time.utc(使用 :utc)或 Time.local(使用 :local)。默认情况下设置为 :utc。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 218 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 510 def self.disconnect_all! ConnectionAdapters::PoolConfig.disconnect_all! end
dump_schema_after_migration 链接
指定在 bin/rails db:migrate 命令结束时是否应该进行模式转储。默认情况下为 true,这对开发环境很有用。在生产环境中,模式转储很少需要,因此理想情况下应该为 false。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 409 singleton_class.attr_accessor :dump_schema_after_migration
dump_schemas 链接
指定在调用 db:schema:dump 时要转储哪些数据库模式。如果值为 :schema_search_path(默认值),则会转储 schema_search_path 中列出的所有模式。使用 :all 转储所有模式,无论 schema_search_path 如何,或者使用逗号分隔的模式字符串来创建自定义列表。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 419 singleton_class.attr_accessor :dump_schemas
eager_load!() 链接
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 499 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
error_on_ignored_order 链接
指定在执行批量查询时,如果查询具有被忽略的排序,是否应该引发错误。在应用中,被忽略的范围是错误,而不是警告,在这种情况下很有用。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 380 singleton_class.attr_accessor :error_on_ignored_order
gem_version() 链接
返回当前加载的 Active Record 版本,作为 Gem::Version
。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record/gem_version.rb, line 5 def self.gem_version Gem::Version.new VERSION::STRING end
generate_secure_token_on 链接
控制何时为 has_secure_token
声明生成值。默认为 :create
。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 460 singleton_class.attr_accessor :generate_secure_token_on
global_executor_concurrency=(global_executor_concurrency) 链接
设置 global_executor_concurrency
。此配置值只能与全局线程池异步查询执行器一起使用。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 298 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 the executor is nil or set to `:multi_thread_pool`. For multiple thread pools, please set the concurrency in your database configuration." end @global_executor_concurrency = global_executor_concurrency end
lazily_load_schema_cache 链接
延迟加载模式缓存。此选项将在建立连接时加载模式缓存,而不是在启动时。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 189 singleton_class.attr_accessor :lazily_load_schema_cache
marshalling_format_version() 链接
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 463 def self.marshalling_format_version Marshalling.format_version end
marshalling_format_version=(value) 链接
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 467 def self.marshalling_format_version=(value) Marshalling.format_version = value end
migration_strategy 链接
指定用于执行迁移的策略。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 400 singleton_class.attr_accessor :migration_strategy
permanent_connection_checkout=(value) 链接
定义是否允许、弃用或完全禁止 ActiveRecord::Base.connection
。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 314 def self.permanent_connection_checkout=(value) unless [true, :deprecated, :disallowed].include?(value) raise ArgumentError, "permanent_connection_checkout must be one of: `true`, `:deprecated` or `:disallowed`" end @permanent_connection_checkout = value end
protocol_adapters 链接
提供数据库协议/DBMS 和要使用的底层数据库适配器之间的映射。这仅由 DATABASE_URL
环境变量使用。
示例
DATABASE_URL="mysql://myuser:mypass@localhost/somedatabase"
上面的 URL 指定 MySQL 是所需的协议/DBMS,然后应用程序配置可以决定使用哪个适配器。对于此示例,默认映射是从 mysql
到 mysql2
,但也支持 :trilogy
。
ActiveRecord.protocol_adapters.mysql = "mysql2"
协议名称是任意的,可以注册外部数据库适配器并在此处设置。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 490 singleton_class.attr_accessor :protocol_adapters
queues 链接
指定后台作业使用的队列名称。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 336 singleton_class.attr_accessor :queues
raise_int_wider_than_64bit 链接
应用程序可配置的布尔值,表示当 PostgreSQLAdapter 提供比带符号 64 位表示更宽的整数时,是否引发异常。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 446 singleton_class.attr_accessor :raise_int_wider_than_64bit
schema_cache_ignored_table?(table_name) 链接
通过检查 schema_cache_ignored_tables
选项,检查 table_name
是否被忽略。
ActiveRecord.schema_cache_ignored_table?(:developers)
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 205 def self.schema_cache_ignored_table?(table_name) ActiveRecord.schema_cache_ignored_tables.any? do |ignored| ignored === table_name end end
schema_cache_ignored_tables 链接
转储模式缓存时要忽略的表或正则表达式列表,用于匹配要忽略的表。例如,如果将其设置为 +[/^_/]+,则模式缓存将不会转储以下划线开头的表。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 197 singleton_class.attr_accessor :schema_cache_ignored_tables
schema_format 链接
指定使用 Rails 的 Rakefile 转储数据库模式时要使用的格式。如果为 :sql,则模式将作为(可能是特定于数据库的)SQL 语句转储。如果为 :ruby,则模式将作为 ActiveRecord::Schema
文件转储,该文件可以加载到支持迁移的任何数据库中。如果希望为开发和测试环境使用不同的数据库适配器,请使用 :ruby。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 372 singleton_class.attr_accessor :schema_format
timestamped_migrations 链接
指定是否为迁移版本使用时间戳。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 386 singleton_class.attr_accessor :timestamped_migrations
use_yaml_unsafe_load 链接
应用程序可配置的布尔值,指示 YAML Coder 如果设置为 true,则使用不安全的加载。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 438 singleton_class.attr_accessor :use_yaml_unsafe_load
validate_migration_timestamps 链接
指定是否验证迁移时间戳。如果设置,则如果时间戳比与当前时间相关联的时间戳提前一天以上,则会引发错误。timestamped_migrations
必须设置为 true。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 394 singleton_class.attr_accessor :validate_migration_timestamps
verbose_query_logs 链接
指定是否在相关查询下方记录调用数据库查询的方法。默认值为 false。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 329 singleton_class.attr_accessor :verbose_query_logs
verify_foreign_keys_for_fixtures 链接
如果为 true,Rails
将在加载 fixtures 后验证数据库中的所有外键。如果存在任何外键违规,将引发错误,表明 fixtures 编写不正确。受 PostgreSQL 和 SQLite 支持。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 428 singleton_class.attr_accessor :verify_foreign_keys_for_fixtures
version() 链接
返回当前加载的 Active Record 版本,作为 Gem::Version
。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record/version.rb, line 7 def self.version gem_version end
yaml_column_permitted_classes 链接
应用程序可配置的数组,为 YAML Coder 中的 Psych safe_load 提供额外的允许类。
来源:显示 | 在 GitHub 上
# File activerecord/lib/active_record.rb, line 453 singleton_class.attr_accessor :yaml_column_permitted_classes