Script 'mail_helper' called by obssrc
Hello community,
here is the log from the commit of package rubygem-activerecord-7.0 for
openSUSE:Factory checked in at 2023-07-03 17:43:12
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/rubygem-activerecord-7.0 (Old)
and /work/SRC/openSUSE:Factory/.rubygem-activerecord-7.0.new.13546 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "rubygem-activerecord-7.0"
Mon Jul 3 17:43:12 2023 rev:9 rq:1096443 version:7.0.5.1
Changes:
--------
---
/work/SRC/openSUSE:Factory/rubygem-activerecord-7.0/rubygem-activerecord-7.0.changes
2023-04-21 18:47:50.332191388 +0200
+++
/work/SRC/openSUSE:Factory/.rubygem-activerecord-7.0.new.13546/rubygem-activerecord-7.0.changes
2023-07-03 17:43:16.300890348 +0200
@@ -1,0 +2,12 @@
+Tue Jun 27 19:31:11 UTC 2023 - Mykola Krachkovsky <[email protected]>
+
+- updated to version 7.0.5.1
+ *
https://rubyonrails.org/2023/6/26/Rails-Versions-7-0-5-1-6-1-7-4-have-been-released
+
+-------------------------------------------------------------------
+Mon Jun 26 19:12:31 UTC 2023 - Mykola Krachkovsky <[email protected]>
+
+- updated to version 7.0.5
+ * https://rubyonrails.org/2023/5/24/Rails-7-0-5-has-been-released
+
+-------------------------------------------------------------------
Old:
----
activerecord-7.0.4.3.gem
New:
----
activerecord-7.0.5.1.gem
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ rubygem-activerecord-7.0.spec ++++++
--- /var/tmp/diff_new_pack.cRkhZW/_old 2023-07-03 17:43:16.932894069 +0200
+++ /var/tmp/diff_new_pack.cRkhZW/_new 2023-07-03 17:43:16.936894093 +0200
@@ -24,7 +24,7 @@
#
Name: rubygem-activerecord-7.0
-Version: 7.0.4.3
+Version: 7.0.5.1
Release: 0
%define mod_name activerecord
%define mod_full_name %{mod_name}-%{version}
++++++ activerecord-7.0.4.3.gem -> activerecord-7.0.5.1.gem ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/CHANGELOG.md new/CHANGELOG.md
--- old/CHANGELOG.md 2023-03-13 19:52:46.000000000 +0100
+++ new/CHANGELOG.md 2023-06-26 23:35:10.000000000 +0200
@@ -1,3 +1,105 @@
+## Rails 7.0.5.1 (June 26, 2023) ##
+
+* No changes.
+
+
+## Rails 7.0.5 (May 24, 2023) ##
+
+* Type cast `#attribute_changed?` `:from` and `:to` options.
+
+ *Andrew Novoselac*
+
+* Fix `index_exists?` when column is an array.
+
+ *Eileen M. Uchitelle*
+
+* Handle `Date` objects for PostgreSQL `timestamptz` columns.
+
+ *Alex Ghiculescu*
+
+* Fix collation for changing column to non-string.
+
+ *Hartley McGuire*
+
+* Map through subtype in `PostgreSQL::OID::Array`.
+
+ *Jonathan Hefner*
+
+* Store correct environment in `internal_metadata` when run rails
`db:prepare`.
+
+ *fatkodima*
+
+* Make sure `ActiveRecord::Relation#sum` works with objects that implement
`#coerce` without deprecation.
+
+ *Alex Ghiculescu*
+
+* Fix retrieving foreign keys referencing tables named like keywords in
PostgreSQL and MySQL.
+
+ *fatkodima*
+
+* Support UUIDs in Disable Joins.
+
+ *Samuel Cochran*
+
+* Fix Active Record's explain for queries starting with comments.
+
+ *fatkodima*
+
+* Fix incorrectly preloading through association records when middle
association has been loaded.
+
+ *Joshua Young*
+
+* Fix where.missing and where.associated for parent/child associations.
+
+ *fatkodima*
+
+* Fix Enumerable#in_order_of to preserve duplicates.
+
+ *fatkodima*
+
+* Fix autoincrement on primary key for mysql.
+
+ *Eileen M. Uchitelle*
+
+* Restore ability to redefine column in `create_table` for Rails 5.2
migrations.
+
+ *fatkodima*
+
+* Fix schema cache dumping of virtual columns.
+
+ *fatkodima*
+
+* Fix Active Record grouped calculations on joined tables on column present
in both tables.
+
+ *fatkodima*
+
+* Fix mutation detection for serialized attributes backed by binary columns.
+
+ *Jean Boussier*
+
+* Fix a bug where using groups and counts with long table names would return
incorrect results.
+
+ *Shota Toguchi*, *Yusaku Ono*
+
+* Use connection from `#with_raw_connection` in `#quote_string`.
+
+ Prior to this change, virtual datetime columns did not have the same
+ default precision as regular datetime columns, resulting in the following
+ being erroneously equivalent:
+
+ t.virtual :name, type: datetime, as: "expression"
+ t.virtual :name, type: datetime, precision: nil, as: "expression"
+
+ This change fixes the default precision lookup, so virtual and regular
+ datetime column default precisions match.
+
+ *Sam Bostock*
+
+* Fix a case where the query cache can return wrong values. See #46044
+
+ *Aaron Patterson*
+
+
## Rails 7.0.4.3 (March 13, 2023) ##
* No changes.
@@ -17,7 +119,7 @@
carefully crafted input.
This commit makes the sanitization more robust by replacing any
- occurrances of "/*" or "*/" with "/ *" or "* /". It also performs a
+ occurrences of "/*" or "*/" with "/ *" or "* /". It also performs a
first pass to remove one surrounding comment to avoid compatibility
issues for users relying on the existing removal.
@@ -142,21 +244,21 @@
This adds two new configuration options The configuration options are as
follows:
-
- * `config.active_storage.use_yaml_unsafe_load`
-
+
+ * `config.active_record.use_yaml_unsafe_load`
+
When set to true, this configuration option tells Rails to use the old
"unsafe" YAML loading strategy, maintaining the existing behavior but
leaving
the possible escalation vulnerability in place. Setting this option to
true
is *not* recommended, but can aid in upgrading.
-
+
* `config.active_record.yaml_column_permitted_classes`
-
+
The "safe YAML" loading method does not allow all classes to be
deserialized
by default. This option allows you to specify classes deemed "safe" in
your
application. For example, if your application uses Symbol and Time in
serialized data, you can add Symbol and Time to the allowed list as
follows:
-
+
```
config.active_record.yaml_column_permitted_classes = [Symbol, Date, Time]
```
Binary files old/checksums.yaml.gz and new/checksums.yaml.gz differ
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/associations/has_one_association.rb
new/lib/active_record/associations/has_one_association.rb
--- old/lib/active_record/associations/has_one_association.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/associations/has_one_association.rb 2023-06-26
23:35:10.000000000 +0200
@@ -87,6 +87,10 @@
replace(record, false)
end
+ def replace_keys(record, force: false)
+ # Has one association doesn't have foreign keys to replace.
+ end
+
def remove_target!(method)
case method
when :delete
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/associations/preloader/through_association.rb
new/lib/active_record/associations/preloader/through_association.rb
--- old/lib/active_record/associations/preloader/through_association.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/associations/preloader/through_association.rb
2023-06-26 23:35:10.000000000 +0200
@@ -74,7 +74,7 @@
end
def middle_records
- through_preloaders.flat_map(&:preloaded_records)
+ through_records_by_owner.values.flatten
end
def through_preloaders
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/associations/singular_association.rb
new/lib/active_record/associations/singular_association.rb
--- old/lib/active_record/associations/singular_association.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/associations/singular_association.rb 2023-06-26
23:35:10.000000000 +0200
@@ -54,11 +54,13 @@
end
def _create_record(attributes, raise_error = false, &block)
- record = build_record(attributes, &block)
- saved = record.save
- set_new_record(record)
- raise RecordInvalid.new(record) if !saved && raise_error
- record
+ reflection.klass.transaction do
+ record = build(attributes, &block)
+ saved = record.save
+ replace_keys(record, force: true)
+ raise RecordInvalid.new(record) if !saved && raise_error
+ record
+ end
end
end
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/associations.rb
new/lib/active_record/associations.rb
--- old/lib/active_record/associations.rb 2023-03-13 19:52:46.000000000
+0100
+++ new/lib/active_record/associations.rb 2023-06-26 23:35:10.000000000
+0200
@@ -586,8 +586,11 @@
# has_many :birthday_events, ->(user) { where(starts_on:
user.birthday) }, class_name: 'Event'
# end
#
- # Note: Joining, eager loading, and preloading of these associations is
not possible.
- # These operations happen before instance creation and the scope will be
called with a +nil+ argument.
+ # Note: Joining or eager loading such associations is not possible
because
+ # those operations happen before instance creation. Such associations
+ # _can_ be preloaded, but doing so will perform N+1 queries because there
+ # will be a different scope for each record (similar to preloading
+ # polymorphic scopes).
#
# == Association callbacks
#
@@ -1600,6 +1603,12 @@
#
# Note that
NestedAttributes::ClassMethods#accepts_nested_attributes_for sets
# <tt>:autosave</tt> to <tt>true</tt>.
+ # [:touch]
+ # If true, the associated object will be touched (the +updated_at+ /
+updated_on+ attributes set to current time)
+ # when this record is either saved or destroyed. If you specify a
symbol, that attribute
+ # will be updated with the current time in addition to the
+updated_at+ / +updated_on+ attribute.
+ # Please note that no validation will be performed when touching,
and only the +after_touch+,
+ # +after_commit+, and +after_rollback+ callbacks will be executed.
# [:inverse_of]
# Specifies the name of the #belongs_to association on the
associated object
# that is the inverse of this #has_one association.
@@ -1747,11 +1756,11 @@
# Note that
NestedAttributes::ClassMethods#accepts_nested_attributes_for
# sets <tt>:autosave</tt> to <tt>true</tt>.
# [:touch]
- # If true, the associated object will be touched (the updated_at/on
attributes set to current time)
+ # If true, the associated object will be touched (the +updated_at+ /
+updated_on+ attributes set to current time)
# when this record is either saved or destroyed. If you specify a
symbol, that attribute
- # will be updated with the current time in addition to the
updated_at/on attribute.
- # Please note that with touching no validation is performed and only
the +after_touch+,
- # +after_commit+ and +after_rollback+ callbacks are executed.
+ # will be updated with the current time in addition to the
+updated_at+ / +updated_on+ attribute.
+ # Please note that no validation will be performed when touching,
and only the +after_touch+,
+ # +after_commit+, and +after_rollback+ callbacks will be executed.
# [:inverse_of]
# Specifies the name of the #has_one or #has_many association on the
associated
# object that is the inverse of this #belongs_to association.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/attribute_methods/read.rb
new/lib/active_record/attribute_methods/read.rb
--- old/lib/active_record/attribute_methods/read.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/attribute_methods/read.rb 2023-06-26
23:35:10.000000000 +0200
@@ -23,7 +23,7 @@
# Returns the value of the attribute identified by <tt>attr_name</tt>
after
# it has been typecast (for example, "2004-12-12" in a date column is
cast
- # to a date object, like Date.new(2004, 12, 12)).
+ # to a date object, like <tt>Date.new(2004, 12, 12)</tt>).
def read_attribute(attr_name, &block)
name = attr_name.to_s
name = self.class.attribute_aliases[name] || name
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/attribute_methods/time_zone_conversion.rb
new/lib/active_record/attribute_methods/time_zone_conversion.rb
--- old/lib/active_record/attribute_methods/time_zone_conversion.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/attribute_methods/time_zone_conversion.rb
2023-06-26 23:35:10.000000000 +0200
@@ -19,8 +19,6 @@
if value.is_a?(Hash)
set_time_zone_without_conversion(super)
- elsif value.is_a?(Range)
- Range.new(user_input_in_time_zone(value.begin),
user_input_in_time_zone(value.end), value.exclude_end?)
elsif value.respond_to?(:in_time_zone)
begin
super(user_input_in_time_zone(value)) || super
@@ -42,8 +40,6 @@
value.in_time_zone
elsif value.respond_to?(:infinite?) && value.infinite?
value
- elsif value.is_a?(Range)
- Range.new(convert_time_to_time_zone(value.begin),
convert_time_to_time_zone(value.end), value.exclude_end?)
else
map_avoiding_infinite_recursion(value) { |v|
convert_time_to_time_zone(v) }
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/attribute_methods.rb
new/lib/active_record/attribute_methods.rb
--- old/lib/active_record/attribute_methods.rb 2023-03-13 19:52:46.000000000
+0100
+++ new/lib/active_record/attribute_methods.rb 2023-06-26 23:35:10.000000000
+0200
@@ -310,8 +310,8 @@
end
# Returns the value of the attribute identified by <tt>attr_name</tt>
after it has been typecast (for example,
- # "2004-12-12" in a date column is cast to a date object, like
Date.new(2004, 12, 12)). It raises
- # <tt>ActiveModel::MissingAttributeError</tt> if the identified attribute
is missing.
+ # "2004-12-12" in a date column is cast to a date object, like
<tt>Date.new(2004, 12, 12)</tt>). It raises
+ # ActiveModel::MissingAttributeError if the identified attribute is
missing.
#
# Note: +:id+ is always present.
#
@@ -331,7 +331,6 @@
end
# Updates the attribute identified by <tt>attr_name</tt> with the
specified +value+.
- # (Alias for the protected #write_attribute method).
#
# class Person < ActiveRecord::Base
# end
@@ -360,10 +359,9 @@
# end
#
# private
- #
- # def print_accessed_fields
- # p @posts.first.accessed_fields
- # end
+ # def print_accessed_fields
+ # p @posts.first.accessed_fields
+ # end
# end
#
# Which allows you to quickly change your code to:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/callbacks.rb
new/lib/active_record/callbacks.rb
--- old/lib/active_record/callbacks.rb 2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/callbacks.rb 2023-06-26 23:35:10.000000000 +0200
@@ -224,14 +224,13 @@
# after_save :do_something_else
#
# private
- #
- # def log_children
- # # Child processing
- # end
- #
- # def do_something_else
- # # Something else
- # end
+ # def log_children
+ # # Child processing
+ # end
+ #
+ # def do_something_else
+ # # Something else
+ # end
# end
#
# In this case the +log_children+ is executed before +do_something_else+.
@@ -249,14 +248,13 @@
# after_commit :do_something_else
#
# private
- #
- # def log_children
- # # Child processing
- # end
- #
- # def do_something_else
- # # Something else
- # end
+ # def log_children
+ # # Child processing
+ # end
+ #
+ # def do_something_else
+ # # Something else
+ # end
# end
#
# In this case the +do_something_else+ is executed before +log_children+.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/abstract/schema_definitions.rb
new/lib/active_record/connection_adapters/abstract/schema_definitions.rb
--- old/lib/active_record/connection_adapters/abstract/schema_definitions.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/abstract/schema_definitions.rb
2023-06-26 23:35:10.000000000 +0200
@@ -411,20 +411,7 @@
name = name.to_s
type = type.to_sym if type
- if @columns_hash[name]
- if @columns_hash[name].primary_key?
- raise ArgumentError, "you can't redefine the primary key column
'#{name}'. To define a custom primary key, pass { id: false } to create_table."
- else
- raise ArgumentError, "you can't define an already defined column
'#{name}'."
- end
- end
-
- if @conn.supports_datetime_with_precision?
- if type == :datetime && !options.key?(:precision)
- options[:precision] = 6
- end
- end
-
+ raise_on_duplicate_column(name)
@columns_hash[name] = new_column_definition(name, type, **options)
if index
@@ -491,6 +478,13 @@
type = integer_like_primary_key_type(type, options)
end
type = aliased_types(type.to_s, type)
+
+ if @conn.supports_datetime_with_precision?
+ if type == :datetime && !options.key?(:precision)
+ options[:precision] = 6
+ end
+ end
+
options[:primary_key] ||= type == :primary_key
options[:null] = false if options[:primary_key]
create_column_definition(name, type, options)
@@ -525,6 +519,16 @@
def integer_like_primary_key_type(type, options)
type
end
+
+ def raise_on_duplicate_column(name)
+ if @columns_hash[name]
+ if @columns_hash[name].primary_key?
+ raise ArgumentError, "you can't redefine the primary key column
'#{name}'. To define a custom primary key, pass { id: false } to create_table."
+ else
+ raise ArgumentError, "you can't define an already defined column
'#{name}'."
+ end
+ end
+ end
end
class AlterTable # :nodoc:
@@ -661,8 +665,8 @@
# end
#
# See {connection.index_exists?}[rdoc-ref:SchemaStatements#index_exists?]
- def index_exists?(column_name, options = {})
- @base.index_exists?(name, column_name, options)
+ def index_exists?(column_name, **options)
+ @base.index_exists?(name, column_name, **options)
end
# Renames the given index on the table.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/abstract/schema_statements.rb
new/lib/active_record/connection_adapters/abstract/schema_statements.rb
--- old/lib/active_record/connection_adapters/abstract/schema_statements.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/abstract/schema_statements.rb
2023-06-26 23:35:10.000000000 +0200
@@ -98,6 +98,7 @@
#
def index_exists?(table_name, column_name, **options)
checks = []
+ column_name = options[:column] if column_name.nil?
if column_name.present?
column_names = Array(column_name).map(&:to_s)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/abstract_adapter.rb
new/lib/active_record/connection_adapters/abstract_adapter.rb
--- old/lib/active_record/connection_adapters/abstract_adapter.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/abstract_adapter.rb
2023-06-26 23:35:10.000000000 +0200
@@ -593,6 +593,10 @@
#
# This is useful for when you need to call a proprietary method such as
# PostgreSQL's lo_* methods.
+ #
+ # Active Record cannot track if the database is getting modified using
+ # this client. If that is the case, generally you'll want to invalidate
+ # the query cache using +ActiveRecord::Base.clear_query_cache+.
def raw_connection
disable_lazy_transactions!
@connection
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/abstract_mysql_adapter.rb
new/lib/active_record/connection_adapters/abstract_mysql_adapter.rb
--- old/lib/active_record/connection_adapters/abstract_mysql_adapter.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/abstract_mysql_adapter.rb
2023-06-26 23:35:10.000000000 +0200
@@ -403,7 +403,7 @@
fk_info.map do |row|
options = {
- column: row["column"],
+ column: unquote_identifier(row["column"]),
name: row["name"],
primary_key: row["primary_key"]
}
@@ -411,7 +411,7 @@
options[:on_update] = extract_foreign_key_action(row["on_update"])
options[:on_delete] = extract_foreign_key_action(row["on_delete"])
- ForeignKeyDefinition.new(table_name, row["to_table"], options)
+ ForeignKeyDefinition.new(table_name,
unquote_identifier(row["to_table"]), options)
end
end
@@ -619,6 +619,10 @@
end
private
+ def text_type?(type)
+ TYPE_MAP.lookup(type).is_a?(Type::String) ||
TYPE_MAP.lookup(type).is_a?(Type::Text)
+ end
+
def type_map
emulate_booleans ? TYPE_MAP_WITH_BOOLEAN : TYPE_MAP
end
@@ -712,7 +716,7 @@
end
unless options.key?(:collation)
- options[:collation] = column.collation
+ options[:collation] = column.collation if text_type?(type)
end
unless options.key?(:auto_increment)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/mysql/quoting.rb
new/lib/active_record/connection_adapters/mysql/quoting.rb
--- old/lib/active_record/connection_adapters/mysql/quoting.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/mysql/quoting.rb 2023-06-26
23:35:10.000000000 +0200
@@ -51,6 +51,14 @@
"x'#{value.hex}'"
end
+ def unquote_identifier(identifier)
+ if identifier && identifier.start_with?("`")
+ identifier[1..-2]
+ else
+ identifier
+ end
+ end
+
# Override +type_cast+ we pass to mysql2 Date and Time objects instead
# of Strings since mysql2 is able to handle those classes more
efficiently.
def type_cast(value) # :nodoc:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/mysql/schema_definitions.rb
new/lib/active_record/connection_adapters/mysql/schema_definitions.rb
--- old/lib/active_record/connection_adapters/mysql/schema_definitions.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/mysql/schema_definitions.rb
2023-06-26 23:35:10.000000000 +0200
@@ -90,7 +90,10 @@
end
def integer_like_primary_key_type(type, options)
- options[:auto_increment] = true
+ unless options[:auto_increment] == false
+ options[:auto_increment] = true
+ end
+
type
end
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/postgresql/column.rb
new/lib/active_record/connection_adapters/postgresql/column.rb
--- old/lib/active_record/connection_adapters/postgresql/column.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/postgresql/column.rb
2023-06-26 23:35:10.000000000 +0200
@@ -42,11 +42,13 @@
def init_with(coder)
@serial = coder["serial"]
+ @generated = coder["generated"]
super
end
def encode_with(coder)
coder["serial"] = @serial
+ coder["generated"] = @generated
super
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/postgresql/database_statements.rb
new/lib/active_record/connection_adapters/postgresql/database_statements.rb
--- old/lib/active_record/connection_adapters/postgresql/database_statements.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/postgresql/database_statements.rb
2023-06-26 23:35:10.000000000 +0200
@@ -57,11 +57,7 @@
fields.each_with_index do |fname, i|
ftype = result.ftype i
fmod = result.fmod i
- case type = get_oid_type(ftype, fmod, fname)
- when Type::Integer, Type::Float, OID::Decimal, Type::String,
Type::DateTime, Type::Boolean
- # skip if a column has already been type casted by pg decoders
- else types[fname] = type
- end
+ types[fname] = get_oid_type(ftype, fmod, fname)
end
build_result(columns: fields, rows: result.values, column_types:
types)
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/postgresql/oid/array.rb
new/lib/active_record/connection_adapters/postgresql/oid/array.rb
--- old/lib/active_record/connection_adapters/postgresql/oid/array.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/postgresql/oid/array.rb
2023-06-26 23:35:10.000000000 +0200
@@ -65,7 +65,7 @@
end
def map(value, &block)
- value.map(&block)
+ value.map { |v| subtype.map(v, &block) }
end
def changed_in_place?(raw_old_value, new_value)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/postgresql/oid/timestamp_with_time_zone.rb
new/lib/active_record/connection_adapters/postgresql/oid/timestamp_with_time_zone.rb
---
old/lib/active_record/connection_adapters/postgresql/oid/timestamp_with_time_zone.rb
2023-03-13 19:52:46.000000000 +0100
+++
new/lib/active_record/connection_adapters/postgresql/oid/timestamp_with_time_zone.rb
2023-06-26 23:35:10.000000000 +0200
@@ -13,7 +13,7 @@
return if value.blank?
time = super
- return time if time.is_a?(ActiveSupport::TimeWithZone)
+ return time unless time.acts_like?(:time)
# While in UTC mode, the PG gem may not return times back in "UTC"
even if they were provided to Postgres in UTC.
# We prefer times always in UTC, so here we convert back.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/postgresql/schema_statements.rb
new/lib/active_record/connection_adapters/postgresql/schema_statements.rb
--- old/lib/active_record/connection_adapters/postgresql/schema_statements.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/postgresql/schema_statements.rb
2023-06-26 23:35:10.000000000 +0200
@@ -498,7 +498,7 @@
fk_info.map do |row|
options = {
- column: row["column"],
+ column: Utils.unquote_identifier(row["column"]),
name: row["name"],
primary_key: row["primary_key"]
}
@@ -508,8 +508,9 @@
options[:deferrable] =
extract_foreign_key_deferrable(row["deferrable"], row["deferred"])
options[:validate] = row["valid"]
+ to_table = Utils.unquote_identifier(row["to_table"])
- ForeignKeyDefinition.new(table_name, row["to_table"], options)
+ ForeignKeyDefinition.new(table_name, to_table, options)
end
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/postgresql/utils.rb
new/lib/active_record/connection_adapters/postgresql/utils.rb
--- old/lib/active_record/connection_adapters/postgresql/utils.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/postgresql/utils.rb
2023-06-26 23:35:10.000000000 +0200
@@ -12,7 +12,7 @@
attr_reader :schema, :identifier
def initialize(schema, identifier)
- @schema, @identifier = unquote(schema), unquote(identifier)
+ @schema, @identifier = Utils.unquote_identifier(schema),
Utils.unquote_identifier(identifier)
end
def to_s
@@ -40,15 +40,6 @@
def parts
@parts ||= [@schema, @identifier].compact
end
-
- private
- def unquote(part)
- if part && part.start_with?('"')
- part[1..-2]
- else
- part
- end
- end
end
module Utils # :nodoc:
@@ -74,6 +65,14 @@
end
PostgreSQL::Name.new(schema, table)
end
+
+ def unquote_identifier(identifier)
+ if identifier && identifier.start_with?('"')
+ identifier[1..-2]
+ else
+ identifier
+ end
+ end
end
end
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/connection_adapters/postgresql_adapter.rb
new/lib/active_record/connection_adapters/postgresql_adapter.rb
--- old/lib/active_record/connection_adapters/postgresql_adapter.rb
2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/connection_adapters/postgresql_adapter.rb
2023-06-26 23:35:10.000000000 +0200
@@ -977,7 +977,7 @@
PG::TextDecoder::TimestampUtc :
PG::TextDecoder::TimestampWithoutTimeZone
- @timestamp_decoder = decoder_class.new(@timestamp_decoder.to_h)
+ @timestamp_decoder = decoder_class.new(**@timestamp_decoder.to_h)
@connection.type_map_for_results.add_coder(@timestamp_decoder)
@default_timezone = ActiveRecord.default_timezone
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/lib/active_record/disable_joins_association_relation.rb
new/lib/active_record/disable_joins_association_relation.rb
--- old/lib/active_record/disable_joins_association_relation.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/disable_joins_association_relation.rb 2023-06-26
23:35:10.000000000 +0200
@@ -30,7 +30,7 @@
record[key]
end
- records = ids.flat_map { |id| records_by_id[id.to_i] }
+ records = ids.flat_map { |id| records_by_id[id] }
records.compact!
@records = records
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/explain_subscriber.rb
new/lib/active_record/explain_subscriber.rb
--- old/lib/active_record/explain_subscriber.rb 2023-03-13 19:52:46.000000000
+0100
+++ new/lib/active_record/explain_subscriber.rb 2023-06-26 23:35:10.000000000
+0200
@@ -21,7 +21,7 @@
# On the other hand, we want to monitor the performance of our real
database
# queries, not the performance of the access to the query cache.
IGNORED_PAYLOADS = %w(SCHEMA EXPLAIN)
- EXPLAINED_SQLS = /\A\s*(with|select|update|delete|insert)\b/i
+ EXPLAINED_SQLS =
/\A\s*(\/\*.*\*\/)?\s*(with|select|update|delete|insert)\b/i
def ignore_payload?(payload)
payload[:exception] ||
payload[:cached] ||
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/gem_version.rb
new/lib/active_record/gem_version.rb
--- old/lib/active_record/gem_version.rb 2023-03-13 19:52:46.000000000
+0100
+++ new/lib/active_record/gem_version.rb 2023-06-26 23:35:10.000000000
+0200
@@ -9,8 +9,8 @@
module VERSION
MAJOR = 7
MINOR = 0
- TINY = 4
- PRE = "3"
+ TINY = 5
+ PRE = "1"
STRING = [MAJOR, MINOR, TINY, PRE].compact.join(".")
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/middleware/database_selector.rb
new/lib/active_record/middleware/database_selector.rb
--- old/lib/active_record/middleware/database_selector.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/middleware/database_selector.rb 2023-06-26
23:35:10.000000000 +0200
@@ -43,9 +43,9 @@
# config.active_record.database_resolver = MyResolver
# config.active_record.database_resolver_context = MyResolver::MySession
#
- # Note: If you are using `rails new my_app --minimal` you will need to call
- # `require "active_support/core_ext/integer/time"` to load the libraries
- # for +Time+.
+ # Note: If you are using <tt>rails new my_app --minimal</tt> you will need
+ # to call <tt>require "active_support/core_ext/integer/time"</tt> to load
+ # the core extension in order to use +2.seconds+
class DatabaseSelector
def initialize(app, resolver_klass = nil, context_klass = nil, options =
{})
@app = app
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/migration/command_recorder.rb
new/lib/active_record/migration/command_recorder.rb
--- old/lib/active_record/migration/command_recorder.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/migration/command_recorder.rb 2023-06-26
23:35:10.000000000 +0200
@@ -12,7 +12,6 @@
# * add_index
# * add_reference
# * add_timestamps
- # * change_column
# * change_column_default (must supply a +:from+ and +:to+ option)
# * change_column_null
# * change_column_comment (must supply a +:from+ and +:to+ option)
@@ -24,7 +23,7 @@
# * drop_table (must supply a block)
# * enable_extension
# * remove_column (must supply a type)
- # * remove_columns (must specify at least one column name or more)
+ # * remove_columns (must supply a +:type+ option)
# * remove_foreign_key (must supply a second table)
# * remove_check_constraint
# * remove_index
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/migration/compatibility.rb
new/lib/active_record/migration/compatibility.rb
--- old/lib/active_record/migration/compatibility.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/migration/compatibility.rb 2023-06-26
23:35:10.000000000 +0200
@@ -159,6 +159,13 @@
options[:precision] ||= nil
super
end
+
+ private
+ def raise_on_if_exist_options(options)
+ end
+
+ def raise_on_duplicate_column(name)
+ end
end
module CommandRecorder
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/migration.rb
new/lib/active_record/migration.rb
--- old/lib/active_record/migration.rb 2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/migration.rb 2023-06-26 23:35:10.000000000 +0200
@@ -1338,7 +1338,7 @@
# Stores the current environment in the database.
def record_environment
return if down?
- ActiveRecord::InternalMetadata[:environment] =
ActiveRecord::Base.connection.migration_context.current_environment
+ ActiveRecord::InternalMetadata[:environment] =
ActiveRecord::Base.connection.pool.db_config.env_name
end
def ran?(migration)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/relation/calculations.rb
new/lib/active_record/relation/calculations.rb
--- old/lib/active_record/relation/calculations.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/relation/calculations.rb 2023-06-26
23:35:10.000000000 +0200
@@ -4,6 +4,47 @@
module ActiveRecord
module Calculations
+ class ColumnAliasTracker # :nodoc:
+ def initialize(connection)
+ @connection = connection
+ @aliases = Hash.new(0)
+ end
+
+ def alias_for(field)
+ aliased_name = column_alias_for(field)
+
+ if @aliases[aliased_name] == 0
+ @aliases[aliased_name] = 1
+ aliased_name
+ else
+ # Update the count
+ count = @aliases[aliased_name] += 1
+ "#{truncate(aliased_name)}_#{count}"
+ end
+ end
+
+ private
+ # Converts the given field to the value that the database adapter
returns as
+ # a usable column name:
+ #
+ # column_alias_for("users.id") # => "users_id"
+ # column_alias_for("sum(id)") # => "sum_id"
+ # column_alias_for("count(distinct users.id)") # =>
"count_distinct_users_id"
+ # column_alias_for("count(*)") # => "count_all"
+ def column_alias_for(field)
+ column_alias = +field
+ column_alias.gsub!(/\*/, "all")
+ column_alias.gsub!(/\W+/, " ")
+ column_alias.strip!
+ column_alias.gsub!(/ +/, "_")
+ @connection.table_alias_for(column_alias)
+ end
+
+ def truncate(name)
+ name.slice(0, @connection.table_alias_length - 2)
+ end
+ end
+
# Count the records.
#
# Person.count
@@ -86,7 +127,7 @@
def sum(identity_or_column = nil, &block)
if block_given?
values = map(&block)
- if identity_or_column.nil? && (values.first.is_a?(Numeric) ||
values.first(1) == [])
+ if identity_or_column.nil? && (values.first.is_a?(Numeric) ||
values.first(1) == [] || values.first.respond_to?(:coerce))
identity_or_column = 0
end
@@ -336,14 +377,16 @@
end
group_fields = arel_columns(group_fields)
+ column_alias_tracker = ColumnAliasTracker.new(connection)
+
group_aliases = group_fields.map { |field|
field = connection.visitor.compile(field) if Arel.arel_node?(field)
- column_alias_for(field.to_s.downcase)
+ column_alias_tracker.alias_for(field.to_s.downcase)
}
group_columns = group_aliases.zip(group_fields)
column = aggregate_column(column_name)
- column_alias = column_alias_for("#{operation}
#{column_name.to_s.downcase}")
+ column_alias = column_alias_tracker.alias_for("#{operation}
#{column_name.to_s.downcase}")
select_value = operation_over_aggregate_column(column, operation,
distinct)
select_value.as(connection.quote_column_name(column_alias))
@@ -372,9 +415,10 @@
end
key_types = group_columns.each_with_object({}) do |(aliaz, col_name),
types|
- types[aliaz] = type_for(col_name) do
- calculated_data.column_types.fetch(aliaz, Type.default_value)
- end
+ types[aliaz] = col_name.try(:type_caster) ||
+ type_for(col_name) do
+ calculated_data.column_types.fetch(aliaz, Type.default_value)
+ end
end
hash_rows = calculated_data.cast_values(key_types).map! do |row|
@@ -398,23 +442,6 @@
end
end
- # Converts the given field to the value that the database adapter
returns as
- # a usable column name:
- #
- # column_alias_for("users.id") # => "users_id"
- # column_alias_for("sum(id)") # => "sum_id"
- # column_alias_for("count(distinct users.id)") # =>
"count_distinct_users_id"
- # column_alias_for("count(*)") # => "count_all"
- def column_alias_for(field)
- column_alias = +field
- column_alias.gsub!(/\*/, "all")
- column_alias.gsub!(/\W+/, " ")
- column_alias.strip!
- column_alias.gsub!(/ +/, "_")
-
- connection.table_alias_for(column_alias)
- end
-
def type_for(field, &block)
field_name = field.respond_to?(:name) ? field.name.to_s :
field.to_s.split(".").last
@klass.type_for_attribute(field_name, &block)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/relation/predicate_builder.rb
new/lib/active_record/relation/predicate_builder.rb
--- old/lib/active_record/relation/predicate_builder.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/relation/predicate_builder.rb 2023-06-26
23:35:10.000000000 +0200
@@ -65,7 +65,8 @@
end
def build_bind_attribute(column_name, value)
- Relation::QueryAttribute.new(column_name, value, table.type(column_name))
+ type = table.type(column_name)
+ Relation::QueryAttribute.new(column_name, type.immutable_value(value),
type)
end
def resolve_arel_attribute(table_name, column_name, &block)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/relation/query_methods.rb
new/lib/active_record/relation/query_methods.rb
--- old/lib/active_record/relation/query_methods.rb 2023-03-13
19:52:46.000000000 +0100
+++ new/lib/active_record/relation/query_methods.rb 2023-06-26
23:35:10.000000000 +0200
@@ -77,7 +77,7 @@
associations.each do |association|
reflection = scope_association_reflection(association)
@scope.joins!(association)
- self.not(reflection.table_name => {
reflection.association_primary_key => nil })
+ self.not(association => { reflection.association_primary_key => nil
})
end
@scope
@@ -105,7 +105,7 @@
associations.each do |association|
reflection = scope_association_reflection(association)
@scope.left_outer_joins!(association)
- @scope.where!(reflection.table_name => {
reflection.association_primary_key => nil })
+ @scope.where!(association => { reflection.association_primary_key =>
nil })
end
@scope
@@ -289,7 +289,7 @@
# You can also use one or more strings, which will be used unchanged as
SELECT fields.
#
# Model.select('field AS field_one', 'other_field AS field_two')
- # # => [#<Model id: nil, field: "value", other_field: "value">]
+ # # => [#<Model id: nil, field_one: "value", field_two: "value">]
#
# If an alias was specified, it will be accessible from the resulting
objects:
#
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/schema_dumper.rb
new/lib/active_record/schema_dumper.rb
--- old/lib/active_record/schema_dumper.rb 2023-03-13 19:52:46.000000000
+0100
+++ new/lib/active_record/schema_dumper.rb 2023-06-26 23:35:10.000000000
+0200
@@ -292,6 +292,10 @@
end
def remove_prefix_and_suffix(table)
+ # This method appears at the top when profiling active_record test
cases run.
+ # Avoid costly calculation when there are no prefix and suffix.
+ return table if @options[:table_name_prefix].blank? &&
@options[:table_name_suffix].blank?
+
prefix = Regexp.escape(@options[:table_name_prefix].to_s)
suffix = Regexp.escape(@options[:table_name_suffix].to_s)
table.sub(/\A#{prefix}(.+)#{suffix}\z/, "\\1")
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/store.rb
new/lib/active_record/store.rb
--- old/lib/active_record/store.rb 2023-03-13 19:52:46.000000000 +0100
+++ new/lib/active_record/store.rb 2023-06-26 23:35:10.000000000 +0200
@@ -70,7 +70,7 @@
#
# The stored attribute names can be retrieved using
{.stored_attributes}[rdoc-ref:rdoc-ref:ClassMethods#stored_attributes].
#
- # User.stored_attributes[:settings] # [:color, :homepage,
:two_factor_auth, :login_retry]
+ # User.stored_attributes[:settings] # => [:color, :homepage,
:two_factor_auth, :login_retry]
#
# == Overwriting default accessors
#
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/active_record/type/serialized.rb
new/lib/active_record/type/serialized.rb
--- old/lib/active_record/type/serialized.rb 2023-03-13 19:52:46.000000000
+0100
+++ new/lib/active_record/type/serialized.rb 2023-06-26 23:35:10.000000000
+0200
@@ -63,11 +63,11 @@
def encoded(value)
return if default_value?(value)
payload = coder.dump(value)
- if payload && binary? && payload.encoding != Encoding::BINARY
- payload = payload.dup if payload.frozen?
- payload.force_encoding(Encoding::BINARY)
+ if payload && @subtype.binary?
+ ActiveModel::Type::Binary::Data.new(payload)
+ else
+ payload
end
- payload
end
end
end
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/arel/filter_predications.rb
new/lib/arel/filter_predications.rb
--- old/lib/arel/filter_predications.rb 2023-03-13 19:52:46.000000000 +0100
+++ new/lib/arel/filter_predications.rb 2023-06-26 23:35:10.000000000 +0200
@@ -1,6 +1,6 @@
# frozen_string_literal: true
-module Arel
+module Arel # :nodoc: all
module FilterPredications
def filter(expr)
Nodes::Filter.new(self, expr)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/lib/arel/nodes/filter.rb new/lib/arel/nodes/filter.rb
--- old/lib/arel/nodes/filter.rb 2023-03-13 19:52:46.000000000 +0100
+++ new/lib/arel/nodes/filter.rb 2023-06-26 23:35:10.000000000 +0200
@@ -1,6 +1,6 @@
# frozen_string_literal: true
-module Arel
+module Arel # :nodoc: all
module Nodes
class Filter < Binary
include Arel::WindowPredications
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/metadata new/metadata
--- old/metadata 2023-03-13 19:52:46.000000000 +0100
+++ new/metadata 2023-06-26 23:35:10.000000000 +0200
@@ -1,14 +1,14 @@
--- !ruby/object:Gem::Specification
name: activerecord
version: !ruby/object:Gem::Version
- version: 7.0.4.3
+ version: 7.0.5.1
platform: ruby
authors:
- David Heinemeier Hansson
autorequire:
bindir: bin
cert_chain: []
-date: 2023-03-13 00:00:00.000000000 Z
+date: 2023-06-26 00:00:00.000000000 Z
dependencies:
- !ruby/object:Gem::Dependency
name: activesupport
@@ -16,28 +16,28 @@
requirements:
- - '='
- !ruby/object:Gem::Version
- version: 7.0.4.3
+ version: 7.0.5.1
type: :runtime
prerelease: false
version_requirements: !ruby/object:Gem::Requirement
requirements:
- - '='
- !ruby/object:Gem::Version
- version: 7.0.4.3
+ version: 7.0.5.1
- !ruby/object:Gem::Dependency
name: activemodel
requirement: !ruby/object:Gem::Requirement
requirements:
- - '='
- !ruby/object:Gem::Version
- version: 7.0.4.3
+ version: 7.0.5.1
type: :runtime
prerelease: false
version_requirements: !ruby/object:Gem::Requirement
requirements:
- - '='
- !ruby/object:Gem::Version
- version: 7.0.4.3
+ version: 7.0.5.1
description: Databases on Rails. Build a persistent domain model by mapping
database
tables to Ruby classes. Strong conventions for associations, validations,
aggregations,
migrations, and testing come baked-in.
@@ -434,10 +434,10 @@
- MIT
metadata:
bug_tracker_uri: https://github.com/rails/rails/issues
- changelog_uri:
https://github.com/rails/rails/blob/v7.0.4.3/activerecord/CHANGELOG.md
- documentation_uri: https://api.rubyonrails.org/v7.0.4.3/
+ changelog_uri:
https://github.com/rails/rails/blob/v7.0.5.1/activerecord/CHANGELOG.md
+ documentation_uri: https://api.rubyonrails.org/v7.0.5.1/
mailing_list_uri: https://discuss.rubyonrails.org/c/rubyonrails-talk
- source_code_uri: https://github.com/rails/rails/tree/v7.0.4.3/activerecord
+ source_code_uri: https://github.com/rails/rails/tree/v7.0.5.1/activerecord
rubygems_mfa_required: 'true'
post_install_message:
rdoc_options:
@@ -456,7 +456,7 @@
- !ruby/object:Gem::Version
version: '0'
requirements: []
-rubygems_version: 3.4.3
+rubygems_version: 3.3.3
signing_key:
specification_version: 4
summary: Object-relational mapper framework (part of Rails).