activerecord 6.0.5.1 → 6.1.0.rc1
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of activerecord might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/CHANGELOG.md +764 -916
- data/MIT-LICENSE +1 -1
- data/README.rdoc +3 -3
- data/lib/active_record/aggregations.rb +1 -1
- data/lib/active_record/association_relation.rb +22 -14
- data/lib/active_record/associations/alias_tracker.rb +19 -15
- data/lib/active_record/associations/association.rb +39 -27
- data/lib/active_record/associations/association_scope.rb +11 -15
- data/lib/active_record/associations/belongs_to_association.rb +15 -5
- data/lib/active_record/associations/belongs_to_polymorphic_association.rb +1 -1
- data/lib/active_record/associations/builder/association.rb +9 -3
- data/lib/active_record/associations/builder/belongs_to.rb +10 -7
- data/lib/active_record/associations/builder/collection_association.rb +5 -4
- data/lib/active_record/associations/builder/has_and_belongs_to_many.rb +0 -1
- data/lib/active_record/associations/builder/has_many.rb +6 -2
- data/lib/active_record/associations/builder/has_one.rb +11 -14
- data/lib/active_record/associations/builder/singular_association.rb +1 -1
- data/lib/active_record/associations/collection_association.rb +19 -13
- data/lib/active_record/associations/collection_proxy.rb +12 -5
- data/lib/active_record/associations/foreign_association.rb +13 -0
- data/lib/active_record/associations/has_many_association.rb +24 -2
- data/lib/active_record/associations/has_many_through_association.rb +10 -4
- data/lib/active_record/associations/has_one_association.rb +15 -1
- data/lib/active_record/associations/join_dependency/join_association.rb +29 -14
- data/lib/active_record/associations/join_dependency/join_part.rb +1 -1
- data/lib/active_record/associations/join_dependency.rb +63 -49
- data/lib/active_record/associations/preloader/association.rb +13 -5
- data/lib/active_record/associations/preloader/through_association.rb +1 -1
- data/lib/active_record/associations/preloader.rb +5 -3
- data/lib/active_record/associations/singular_association.rb +1 -1
- data/lib/active_record/associations.rb +114 -11
- data/lib/active_record/attribute_assignment.rb +10 -8
- data/lib/active_record/attribute_methods/before_type_cast.rb +13 -9
- data/lib/active_record/attribute_methods/dirty.rb +1 -11
- data/lib/active_record/attribute_methods/primary_key.rb +6 -2
- data/lib/active_record/attribute_methods/query.rb +3 -6
- data/lib/active_record/attribute_methods/read.rb +8 -11
- data/lib/active_record/attribute_methods/serialization.rb +4 -4
- data/lib/active_record/attribute_methods/time_zone_conversion.rb +12 -13
- data/lib/active_record/attribute_methods/write.rb +12 -20
- data/lib/active_record/attribute_methods.rb +52 -48
- data/lib/active_record/attributes.rb +27 -7
- data/lib/active_record/autosave_association.rb +47 -30
- data/lib/active_record/base.rb +2 -14
- data/lib/active_record/callbacks.rb +32 -22
- data/lib/active_record/coders/yaml_column.rb +2 -14
- data/lib/active_record/connection_adapters/abstract/connection_pool.rb +180 -134
- data/lib/active_record/connection_adapters/abstract/database_limits.rb +2 -44
- data/lib/active_record/connection_adapters/abstract/database_statements.rb +65 -22
- data/lib/active_record/connection_adapters/abstract/query_cache.rb +2 -7
- data/lib/active_record/connection_adapters/abstract/quoting.rb +34 -34
- data/lib/active_record/connection_adapters/abstract/savepoints.rb +3 -3
- data/lib/active_record/connection_adapters/abstract/schema_creation.rb +153 -116
- data/lib/active_record/connection_adapters/abstract/schema_definitions.rb +110 -30
- data/lib/active_record/connection_adapters/abstract/schema_dumper.rb +3 -3
- data/lib/active_record/connection_adapters/abstract/schema_statements.rb +224 -85
- data/lib/active_record/connection_adapters/abstract/transaction.rb +66 -24
- data/lib/active_record/connection_adapters/abstract_adapter.rb +31 -70
- data/lib/active_record/connection_adapters/abstract_mysql_adapter.rb +123 -87
- data/lib/active_record/connection_adapters/column.rb +15 -1
- data/lib/active_record/connection_adapters/deduplicable.rb +29 -0
- data/lib/active_record/connection_adapters/legacy_pool_manager.rb +31 -0
- data/lib/active_record/connection_adapters/mysql/database_statements.rb +22 -24
- data/lib/active_record/connection_adapters/mysql/explain_pretty_printer.rb +1 -1
- data/lib/active_record/connection_adapters/mysql/quoting.rb +1 -1
- data/lib/active_record/connection_adapters/mysql/schema_creation.rb +33 -6
- data/lib/active_record/connection_adapters/mysql/schema_definitions.rb +8 -0
- data/lib/active_record/connection_adapters/mysql/schema_dumper.rb +1 -1
- data/lib/active_record/connection_adapters/mysql/schema_statements.rb +3 -3
- data/lib/active_record/connection_adapters/mysql/type_metadata.rb +10 -1
- data/lib/active_record/connection_adapters/mysql2_adapter.rb +31 -12
- data/lib/active_record/connection_adapters/pool_config.rb +63 -0
- data/lib/active_record/connection_adapters/pool_manager.rb +43 -0
- data/lib/active_record/connection_adapters/postgresql/column.rb +24 -1
- data/lib/active_record/connection_adapters/postgresql/database_statements.rb +12 -53
- data/lib/active_record/connection_adapters/postgresql/oid/cidr.rb +3 -5
- data/lib/active_record/connection_adapters/postgresql/oid/date.rb +2 -2
- data/lib/active_record/connection_adapters/postgresql/oid/date_time.rb +2 -10
- data/lib/active_record/connection_adapters/postgresql/oid/interval.rb +49 -0
- data/lib/active_record/connection_adapters/postgresql/oid/legacy_point.rb +2 -2
- data/lib/active_record/connection_adapters/postgresql/oid/macaddr.rb +25 -0
- data/lib/active_record/connection_adapters/postgresql/oid/money.rb +2 -2
- data/lib/active_record/connection_adapters/postgresql/oid/point.rb +2 -2
- data/lib/active_record/connection_adapters/postgresql/oid/uuid.rb +11 -1
- data/lib/active_record/connection_adapters/postgresql/oid.rb +2 -0
- data/lib/active_record/connection_adapters/postgresql/quoting.rb +4 -4
- data/lib/active_record/connection_adapters/postgresql/referential_integrity.rb +1 -1
- data/lib/active_record/connection_adapters/postgresql/schema_creation.rb +5 -1
- data/lib/active_record/connection_adapters/postgresql/schema_statements.rb +61 -29
- data/lib/active_record/connection_adapters/postgresql/type_metadata.rb +8 -0
- data/lib/active_record/connection_adapters/postgresql_adapter.rb +72 -55
- data/lib/active_record/connection_adapters/schema_cache.rb +98 -15
- data/lib/active_record/connection_adapters/sql_type_metadata.rb +10 -0
- data/lib/active_record/connection_adapters/sqlite3/database_statements.rb +30 -5
- data/lib/active_record/connection_adapters/sqlite3/quoting.rb +1 -1
- data/lib/active_record/connection_adapters/sqlite3/schema_creation.rb +5 -1
- data/lib/active_record/connection_adapters/sqlite3/schema_statements.rb +36 -3
- data/lib/active_record/connection_adapters/sqlite3_adapter.rb +48 -50
- data/lib/active_record/connection_adapters.rb +50 -0
- data/lib/active_record/connection_handling.rb +210 -71
- data/lib/active_record/core.rb +214 -58
- data/lib/active_record/database_configurations/connection_url_resolver.rb +98 -0
- data/lib/active_record/database_configurations/database_config.rb +52 -9
- data/lib/active_record/database_configurations/hash_config.rb +54 -8
- data/lib/active_record/database_configurations/url_config.rb +15 -40
- data/lib/active_record/database_configurations.rb +124 -85
- data/lib/active_record/delegated_type.rb +209 -0
- data/lib/active_record/destroy_association_async_job.rb +36 -0
- data/lib/active_record/enum.rb +33 -23
- data/lib/active_record/errors.rb +47 -12
- data/lib/active_record/explain.rb +9 -4
- data/lib/active_record/explain_subscriber.rb +1 -1
- data/lib/active_record/fixture_set/file.rb +10 -17
- data/lib/active_record/fixture_set/model_metadata.rb +1 -2
- data/lib/active_record/fixture_set/render_context.rb +1 -1
- data/lib/active_record/fixture_set/table_row.rb +2 -2
- data/lib/active_record/fixtures.rb +54 -8
- data/lib/active_record/gem_version.rb +3 -3
- data/lib/active_record/inheritance.rb +40 -18
- data/lib/active_record/insert_all.rb +32 -5
- data/lib/active_record/integration.rb +3 -5
- data/lib/active_record/internal_metadata.rb +15 -4
- data/lib/active_record/legacy_yaml_adapter.rb +7 -3
- data/lib/active_record/locking/optimistic.rb +13 -16
- data/lib/active_record/locking/pessimistic.rb +6 -2
- data/lib/active_record/log_subscriber.rb +26 -8
- data/lib/active_record/middleware/database_selector/resolver/session.rb +3 -0
- data/lib/active_record/middleware/database_selector/resolver.rb +5 -0
- data/lib/active_record/middleware/database_selector.rb +4 -1
- data/lib/active_record/migration/command_recorder.rb +47 -27
- data/lib/active_record/migration/compatibility.rb +67 -17
- data/lib/active_record/migration.rb +113 -83
- data/lib/active_record/model_schema.rb +88 -42
- data/lib/active_record/nested_attributes.rb +2 -3
- data/lib/active_record/no_touching.rb +1 -1
- data/lib/active_record/persistence.rb +50 -45
- data/lib/active_record/query_cache.rb +15 -5
- data/lib/active_record/querying.rb +11 -6
- data/lib/active_record/railtie.rb +61 -59
- data/lib/active_record/railties/databases.rake +253 -98
- data/lib/active_record/readonly_attributes.rb +4 -0
- data/lib/active_record/reflection.rb +59 -44
- data/lib/active_record/relation/batches/batch_enumerator.rb +25 -9
- data/lib/active_record/relation/batches.rb +38 -31
- data/lib/active_record/relation/calculations.rb +100 -43
- data/lib/active_record/relation/finder_methods.rb +44 -14
- data/lib/active_record/relation/from_clause.rb +1 -1
- data/lib/active_record/relation/merger.rb +20 -23
- data/lib/active_record/relation/predicate_builder/array_handler.rb +8 -9
- data/lib/active_record/relation/predicate_builder/association_query_value.rb +2 -2
- data/lib/active_record/relation/predicate_builder/polymorphic_array_value.rb +3 -3
- data/lib/active_record/relation/predicate_builder/relation_handler.rb +1 -1
- data/lib/active_record/relation/predicate_builder.rb +57 -33
- data/lib/active_record/relation/query_methods.rb +319 -196
- data/lib/active_record/relation/record_fetch_warning.rb +3 -3
- data/lib/active_record/relation/spawn_methods.rb +6 -5
- data/lib/active_record/relation/where_clause.rb +104 -57
- data/lib/active_record/relation.rb +90 -64
- data/lib/active_record/result.rb +41 -33
- data/lib/active_record/runtime_registry.rb +2 -2
- data/lib/active_record/sanitization.rb +6 -17
- data/lib/active_record/schema_dumper.rb +34 -4
- data/lib/active_record/schema_migration.rb +0 -4
- data/lib/active_record/scoping/named.rb +1 -17
- data/lib/active_record/secure_token.rb +16 -8
- data/lib/active_record/serialization.rb +5 -3
- data/lib/active_record/signed_id.rb +116 -0
- data/lib/active_record/statement_cache.rb +20 -4
- data/lib/active_record/store.rb +2 -2
- data/lib/active_record/suppressor.rb +2 -2
- data/lib/active_record/table_metadata.rb +36 -52
- data/lib/active_record/tasks/database_tasks.rb +139 -113
- data/lib/active_record/tasks/mysql_database_tasks.rb +34 -35
- data/lib/active_record/tasks/postgresql_database_tasks.rb +24 -26
- data/lib/active_record/tasks/sqlite_database_tasks.rb +13 -9
- data/lib/active_record/test_databases.rb +5 -4
- data/lib/active_record/test_fixtures.rb +36 -33
- data/lib/active_record/timestamp.rb +4 -6
- data/lib/active_record/touch_later.rb +21 -21
- data/lib/active_record/transactions.rb +15 -64
- data/lib/active_record/type/serialized.rb +6 -2
- data/lib/active_record/type.rb +8 -1
- data/lib/active_record/type_caster/connection.rb +0 -1
- data/lib/active_record/type_caster/map.rb +8 -5
- data/lib/active_record/validations/associated.rb +1 -1
- data/lib/active_record/validations/numericality.rb +35 -0
- data/lib/active_record/validations/uniqueness.rb +24 -4
- data/lib/active_record/validations.rb +1 -0
- data/lib/active_record.rb +7 -14
- data/lib/arel/attributes/attribute.rb +4 -0
- data/lib/arel/collectors/bind.rb +5 -0
- data/lib/arel/collectors/composite.rb +8 -0
- data/lib/arel/collectors/sql_string.rb +7 -0
- data/lib/arel/collectors/substitute_binds.rb +7 -0
- data/lib/arel/nodes/binary.rb +82 -8
- data/lib/arel/nodes/bind_param.rb +8 -0
- data/lib/arel/nodes/casted.rb +21 -9
- data/lib/arel/nodes/equality.rb +6 -9
- data/lib/arel/nodes/grouping.rb +3 -0
- data/lib/arel/nodes/homogeneous_in.rb +72 -0
- data/lib/arel/nodes/in.rb +8 -1
- data/lib/arel/nodes/infix_operation.rb +13 -1
- data/lib/arel/nodes/join_source.rb +1 -1
- data/lib/arel/nodes/node.rb +7 -6
- data/lib/arel/nodes/ordering.rb +27 -0
- data/lib/arel/nodes/sql_literal.rb +3 -0
- data/lib/arel/nodes/table_alias.rb +7 -3
- data/lib/arel/nodes/unary.rb +0 -1
- data/lib/arel/nodes.rb +3 -1
- data/lib/arel/predications.rb +12 -18
- data/lib/arel/select_manager.rb +1 -2
- data/lib/arel/table.rb +13 -5
- data/lib/arel/visitors/dot.rb +14 -2
- data/lib/arel/visitors/mysql.rb +11 -1
- data/lib/arel/visitors/postgresql.rb +15 -4
- data/lib/arel/visitors/to_sql.rb +89 -78
- data/lib/arel/visitors.rb +0 -7
- data/lib/arel.rb +5 -13
- data/lib/rails/generators/active_record/migration/migration_generator.rb +1 -0
- data/lib/rails/generators/active_record/migration/templates/create_table_migration.rb.tt +2 -0
- data/lib/rails/generators/active_record/migration/templates/migration.rb.tt +3 -3
- data/lib/rails/generators/active_record/migration.rb +6 -1
- data/lib/rails/generators/active_record/model/model_generator.rb +39 -2
- data/lib/rails/generators/active_record/model/templates/abstract_base_class.rb.tt +7 -0
- metadata +30 -32
- data/lib/active_record/advisory_lock_base.rb +0 -18
- data/lib/active_record/attribute_decorators.rb +0 -88
- data/lib/active_record/connection_adapters/connection_specification.rb +0 -296
- data/lib/active_record/connection_adapters/determine_if_preparable_visitor.rb +0 -29
- data/lib/active_record/define_callbacks.rb +0 -22
- data/lib/active_record/railties/collection_cache_association_loading.rb +0 -34
- data/lib/active_record/relation/predicate_builder/base_handler.rb +0 -18
- data/lib/active_record/relation/where_clause_factory.rb +0 -33
- data/lib/arel/attributes.rb +0 -22
- data/lib/arel/visitors/depth_first.rb +0 -203
- data/lib/arel/visitors/ibm_db.rb +0 -34
- data/lib/arel/visitors/informix.rb +0 -62
- data/lib/arel/visitors/mssql.rb +0 -156
- data/lib/arel/visitors/oracle.rb +0 -158
- data/lib/arel/visitors/oracle12.rb +0 -65
- data/lib/arel/visitors/where_sql.rb +0 -22
data/lib/arel/nodes/casted.rb
CHANGED
@@ -3,30 +3,42 @@
|
|
3
3
|
module Arel # :nodoc: all
|
4
4
|
module Nodes
|
5
5
|
class Casted < Arel::Nodes::NodeExpression # :nodoc:
|
6
|
-
attr_reader :
|
7
|
-
|
8
|
-
|
6
|
+
attr_reader :value, :attribute
|
7
|
+
alias :value_before_type_cast :value
|
8
|
+
|
9
|
+
def initialize(value, attribute)
|
10
|
+
@value = value
|
9
11
|
@attribute = attribute
|
10
12
|
super()
|
11
13
|
end
|
12
14
|
|
13
|
-
def nil?;
|
15
|
+
def nil?; value.nil?; end
|
16
|
+
|
17
|
+
def value_for_database
|
18
|
+
if attribute.able_to_type_cast?
|
19
|
+
attribute.type_cast_for_database(value)
|
20
|
+
else
|
21
|
+
value
|
22
|
+
end
|
23
|
+
end
|
14
24
|
|
15
25
|
def hash
|
16
|
-
[self.class,
|
26
|
+
[self.class, value, attribute].hash
|
17
27
|
end
|
18
28
|
|
19
29
|
def eql?(other)
|
20
30
|
self.class == other.class &&
|
21
|
-
|
22
|
-
|
31
|
+
self.value == other.value &&
|
32
|
+
self.attribute == other.attribute
|
23
33
|
end
|
24
34
|
alias :== :eql?
|
25
35
|
end
|
26
36
|
|
27
37
|
class Quoted < Arel::Nodes::Unary # :nodoc:
|
28
|
-
alias :
|
29
|
-
|
38
|
+
alias :value_for_database :value
|
39
|
+
alias :value_before_type_cast :value
|
40
|
+
|
41
|
+
def nil?; value.nil?; end
|
30
42
|
|
31
43
|
def infinite?
|
32
44
|
value.respond_to?(:infinite?) && value.infinite?
|
data/lib/arel/nodes/equality.rb
CHANGED
@@ -3,16 +3,13 @@
|
|
3
3
|
module Arel # :nodoc: all
|
4
4
|
module Nodes
|
5
5
|
class Equality < Arel::Nodes::Binary
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
end
|
6
|
+
include FetchAttribute
|
7
|
+
|
8
|
+
def equality?; true; end
|
10
9
|
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
}.each do |name|
|
15
|
-
const_set name, Class.new(Equality)
|
10
|
+
def invert
|
11
|
+
Arel::Nodes::NotEqual.new(left, right)
|
12
|
+
end
|
16
13
|
end
|
17
14
|
end
|
18
15
|
end
|
data/lib/arel/nodes/grouping.rb
CHANGED
@@ -0,0 +1,72 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Arel # :nodoc: all
|
4
|
+
module Nodes
|
5
|
+
class HomogeneousIn < Node
|
6
|
+
attr_reader :attribute, :values, :type
|
7
|
+
|
8
|
+
def initialize(values, attribute, type)
|
9
|
+
@values = values
|
10
|
+
@attribute = attribute
|
11
|
+
@type = type
|
12
|
+
end
|
13
|
+
|
14
|
+
def hash
|
15
|
+
ivars.hash
|
16
|
+
end
|
17
|
+
|
18
|
+
def eql?(other)
|
19
|
+
super || (self.class == other.class && self.ivars == other.ivars)
|
20
|
+
end
|
21
|
+
alias :== :eql?
|
22
|
+
|
23
|
+
def equality?
|
24
|
+
type == :in
|
25
|
+
end
|
26
|
+
|
27
|
+
def invert
|
28
|
+
Arel::Nodes::HomogeneousIn.new(values, attribute, type == :in ? :notin : :in)
|
29
|
+
end
|
30
|
+
|
31
|
+
def left
|
32
|
+
attribute
|
33
|
+
end
|
34
|
+
|
35
|
+
def right
|
36
|
+
attribute.quoted_array(values)
|
37
|
+
end
|
38
|
+
|
39
|
+
def table_name
|
40
|
+
attribute.relation.table_alias || attribute.relation.name
|
41
|
+
end
|
42
|
+
|
43
|
+
def column_name
|
44
|
+
attribute.name
|
45
|
+
end
|
46
|
+
|
47
|
+
def casted_values
|
48
|
+
type = attribute.type_caster
|
49
|
+
|
50
|
+
casted_values = values.map do |raw_value|
|
51
|
+
type.serialize(raw_value) if type.serializable?(raw_value)
|
52
|
+
end
|
53
|
+
|
54
|
+
casted_values.compact!
|
55
|
+
casted_values
|
56
|
+
end
|
57
|
+
|
58
|
+
def fetch_attribute(&block)
|
59
|
+
if attribute
|
60
|
+
yield attribute
|
61
|
+
else
|
62
|
+
expr.fetch_attribute(&block)
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
protected
|
67
|
+
def ivars
|
68
|
+
[@attribute, @values, @type]
|
69
|
+
end
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
data/lib/arel/nodes/in.rb
CHANGED
@@ -43,7 +43,19 @@ module Arel # :nodoc: all
|
|
43
43
|
|
44
44
|
class Concat < InfixOperation
|
45
45
|
def initialize(left, right)
|
46
|
-
super("||", left, right)
|
46
|
+
super(:"||", left, right)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
class Contains < InfixOperation
|
51
|
+
def initialize(left, right)
|
52
|
+
super(:"@>", left, right)
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
class Overlaps < InfixOperation
|
57
|
+
def initialize(left, right)
|
58
|
+
super(:"&&", left, right)
|
47
59
|
end
|
48
60
|
end
|
49
61
|
|
@@ -5,7 +5,7 @@ module Arel # :nodoc: all
|
|
5
5
|
###
|
6
6
|
# Class that represents a join source
|
7
7
|
#
|
8
|
-
#
|
8
|
+
# https://www.sqlite.org/syntaxdiagrams.html#join-source
|
9
9
|
|
10
10
|
class JoinSource < Arel::Nodes::Binary
|
11
11
|
def initialize(single_source, joinop = [])
|
data/lib/arel/nodes/node.rb
CHANGED
@@ -6,7 +6,6 @@ module Arel # :nodoc: all
|
|
6
6
|
# Abstract base class for all AST nodes
|
7
7
|
class Node
|
8
8
|
include Arel::FactoryMethods
|
9
|
-
include Enumerable
|
10
9
|
|
11
10
|
###
|
12
11
|
# Factory method to create a Nodes::Not node that has the recipient of
|
@@ -28,6 +27,10 @@ module Arel # :nodoc: all
|
|
28
27
|
Nodes::And.new [self, right]
|
29
28
|
end
|
30
29
|
|
30
|
+
def invert
|
31
|
+
Arel::Nodes::Not.new(self)
|
32
|
+
end
|
33
|
+
|
31
34
|
# FIXME: this method should go away. I don't like people calling
|
32
35
|
# to_sql on non-head nodes. This forces us to walk the AST until we
|
33
36
|
# can find a node that has a "relation" member.
|
@@ -39,12 +42,10 @@ module Arel # :nodoc: all
|
|
39
42
|
collector.value
|
40
43
|
end
|
41
44
|
|
42
|
-
|
43
|
-
def each(&block)
|
44
|
-
return enum_for(:each) unless block_given?
|
45
|
-
|
46
|
-
::Arel::Visitors::DepthFirst.new(block).accept self
|
45
|
+
def fetch_attribute
|
47
46
|
end
|
47
|
+
|
48
|
+
def equality?; false; end
|
48
49
|
end
|
49
50
|
end
|
50
51
|
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module Arel # :nodoc: all
|
4
|
+
module Nodes
|
5
|
+
class Ordering < Unary
|
6
|
+
def nulls_first
|
7
|
+
NullsFirst.new(self)
|
8
|
+
end
|
9
|
+
|
10
|
+
def nulls_last
|
11
|
+
NullsLast.new(self)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
class NullsFirst < Ordering
|
16
|
+
def reverse
|
17
|
+
NullsLast.new(expr.reverse)
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
class NullsLast < Ordering
|
22
|
+
def reverse
|
23
|
+
NullsFirst.new(expr.reverse)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -8,15 +8,19 @@ module Arel # :nodoc: all
|
|
8
8
|
alias :table_alias :name
|
9
9
|
|
10
10
|
def [](name)
|
11
|
-
Attribute.new(self, name)
|
11
|
+
relation.is_a?(Table) ? relation[name, self] : Attribute.new(self, name)
|
12
12
|
end
|
13
13
|
|
14
14
|
def table_name
|
15
15
|
relation.respond_to?(:name) ? relation.name : name
|
16
16
|
end
|
17
17
|
|
18
|
-
def type_cast_for_database(
|
19
|
-
relation.type_cast_for_database(
|
18
|
+
def type_cast_for_database(attr_name, value)
|
19
|
+
relation.type_cast_for_database(attr_name, value)
|
20
|
+
end
|
21
|
+
|
22
|
+
def type_for_attribute(name)
|
23
|
+
relation.type_for_attribute(name)
|
20
24
|
end
|
21
25
|
|
22
26
|
def able_to_type_cast?
|
data/lib/arel/nodes/unary.rb
CHANGED
data/lib/arel/nodes.rb
CHANGED
@@ -18,6 +18,8 @@ require "arel/nodes/false"
|
|
18
18
|
# unary
|
19
19
|
require "arel/nodes/unary"
|
20
20
|
require "arel/nodes/grouping"
|
21
|
+
require "arel/nodes/homogeneous_in"
|
22
|
+
require "arel/nodes/ordering"
|
21
23
|
require "arel/nodes/ascending"
|
22
24
|
require "arel/nodes/descending"
|
23
25
|
require "arel/nodes/unqualified_column"
|
@@ -26,7 +28,7 @@ require "arel/nodes/with"
|
|
26
28
|
# binary
|
27
29
|
require "arel/nodes/binary"
|
28
30
|
require "arel/nodes/equality"
|
29
|
-
require "arel/nodes/in"
|
31
|
+
require "arel/nodes/in"
|
30
32
|
require "arel/nodes/join_source"
|
31
33
|
require "arel/nodes/delete_statement"
|
32
34
|
require "arel/nodes/table_alias"
|
data/lib/arel/predications.rb
CHANGED
@@ -60,13 +60,6 @@ module Arel # :nodoc: all
|
|
60
60
|
case other
|
61
61
|
when Arel::SelectManager
|
62
62
|
Arel::Nodes::In.new(self, other.ast)
|
63
|
-
when Range
|
64
|
-
if $VERBOSE
|
65
|
-
warn <<-eowarn
|
66
|
-
Passing a range to `#in` is deprecated. Call `#between`, instead.
|
67
|
-
eowarn
|
68
|
-
end
|
69
|
-
between(other)
|
70
63
|
when Enumerable
|
71
64
|
Nodes::In.new self, quoted_array(other)
|
72
65
|
else
|
@@ -110,13 +103,6 @@ Passing a range to `#in` is deprecated. Call `#between`, instead.
|
|
110
103
|
case other
|
111
104
|
when Arel::SelectManager
|
112
105
|
Arel::Nodes::NotIn.new(self, other.ast)
|
113
|
-
when Range
|
114
|
-
if $VERBOSE
|
115
|
-
warn <<-eowarn
|
116
|
-
Passing a range to `#not_in` is deprecated. Call `#not_between`, instead.
|
117
|
-
eowarn
|
118
|
-
end
|
119
|
-
not_between(other)
|
120
106
|
when Enumerable
|
121
107
|
Nodes::NotIn.new self, quoted_array(other)
|
122
108
|
else
|
@@ -220,6 +206,18 @@ Passing a range to `#not_in` is deprecated. Call `#not_between`, instead.
|
|
220
206
|
Nodes::Concat.new self, other
|
221
207
|
end
|
222
208
|
|
209
|
+
def contains(other)
|
210
|
+
Arel::Nodes::Contains.new(self, other)
|
211
|
+
end
|
212
|
+
|
213
|
+
def overlaps(other)
|
214
|
+
Arel::Nodes::Overlaps.new(self, other)
|
215
|
+
end
|
216
|
+
|
217
|
+
def quoted_array(others)
|
218
|
+
others.map { |v| quoted_node(v) }
|
219
|
+
end
|
220
|
+
|
223
221
|
private
|
224
222
|
def grouping_any(method_id, others, *extras)
|
225
223
|
nodes = others.map { |expr| send(method_id, expr, *extras) }
|
@@ -237,10 +235,6 @@ Passing a range to `#not_in` is deprecated. Call `#not_between`, instead.
|
|
237
235
|
Nodes.build_quoted(other, self)
|
238
236
|
end
|
239
237
|
|
240
|
-
def quoted_array(others)
|
241
|
-
others.map { |v| quoted_node(v) }
|
242
|
-
end
|
243
|
-
|
244
238
|
def infinity?(value)
|
245
239
|
value.respond_to?(:infinite?) && value.infinite?
|
246
240
|
end
|
data/lib/arel/select_manager.rb
CHANGED
@@ -186,8 +186,7 @@ module Arel # :nodoc: all
|
|
186
186
|
def where_sql(engine = Table.engine)
|
187
187
|
return if @ctx.wheres.empty?
|
188
188
|
|
189
|
-
|
190
|
-
Nodes::SqlLiteral.new viz.accept(@ctx, Collectors::SQLString.new).value
|
189
|
+
Nodes::SqlLiteral.new("WHERE #{Nodes::And.new(@ctx.wheres).to_sql(engine)}")
|
191
190
|
end
|
192
191
|
|
193
192
|
def union(operation, other = nil)
|
data/lib/arel/table.rb
CHANGED
@@ -4,6 +4,7 @@ module Arel # :nodoc: all
|
|
4
4
|
class Table
|
5
5
|
include Arel::Crud
|
6
6
|
include Arel::FactoryMethods
|
7
|
+
include Arel::AliasPredication
|
7
8
|
|
8
9
|
@engine = nil
|
9
10
|
class << self; attr_accessor :engine; end
|
@@ -13,8 +14,9 @@ module Arel # :nodoc: all
|
|
13
14
|
# TableAlias and Table both have a #table_name which is the name of the underlying table
|
14
15
|
alias :table_name :name
|
15
16
|
|
16
|
-
def initialize(name, as: nil, type_caster:
|
17
|
+
def initialize(name, as: nil, klass: nil, type_caster: klass&.type_caster)
|
17
18
|
@name = name.to_s
|
19
|
+
@klass = klass
|
18
20
|
@type_caster = type_caster
|
19
21
|
|
20
22
|
# Sometime AR sends an :as parameter to table, to let the table know
|
@@ -78,8 +80,10 @@ module Arel # :nodoc: all
|
|
78
80
|
from.having expr
|
79
81
|
end
|
80
82
|
|
81
|
-
def [](name)
|
82
|
-
|
83
|
+
def [](name, table = self)
|
84
|
+
name = name.to_s if name.is_a?(Symbol)
|
85
|
+
name = @klass.attribute_aliases[name] || name if @klass
|
86
|
+
Attribute.new(table, name)
|
83
87
|
end
|
84
88
|
|
85
89
|
def hash
|
@@ -96,8 +100,12 @@ module Arel # :nodoc: all
|
|
96
100
|
end
|
97
101
|
alias :== :eql?
|
98
102
|
|
99
|
-
def type_cast_for_database(
|
100
|
-
type_caster.type_cast_for_database(
|
103
|
+
def type_cast_for_database(attr_name, value)
|
104
|
+
type_caster.type_cast_for_database(attr_name, value)
|
105
|
+
end
|
106
|
+
|
107
|
+
def type_for_attribute(name)
|
108
|
+
type_caster.type_for_attribute(name)
|
101
109
|
end
|
102
110
|
|
103
111
|
def able_to_type_cast?
|
data/lib/arel/visitors/dot.rb
CHANGED
@@ -157,7 +157,13 @@ module Arel # :nodoc: all
|
|
157
157
|
end
|
158
158
|
|
159
159
|
def visit_Arel_Nodes_Casted(o)
|
160
|
-
visit_edge o, "
|
160
|
+
visit_edge o, "value"
|
161
|
+
visit_edge o, "attribute"
|
162
|
+
end
|
163
|
+
|
164
|
+
def visit_Arel_Nodes_HomogeneousIn(o)
|
165
|
+
visit_edge o, "values"
|
166
|
+
visit_edge o, "type"
|
161
167
|
visit_edge o, "attribute"
|
162
168
|
end
|
163
169
|
|
@@ -218,7 +224,13 @@ module Arel # :nodoc: all
|
|
218
224
|
alias :visit_Symbol :visit_String
|
219
225
|
alias :visit_Arel_Nodes_SqlLiteral :visit_String
|
220
226
|
|
221
|
-
def visit_Arel_Nodes_BindParam(o)
|
227
|
+
def visit_Arel_Nodes_BindParam(o)
|
228
|
+
edge("value") { visit o.value }
|
229
|
+
end
|
230
|
+
|
231
|
+
def visit_ActiveModel_Attribute(o)
|
232
|
+
edge("value_before_type_cast") { visit o.value_before_type_cast }
|
233
|
+
end
|
222
234
|
|
223
235
|
def visit_Hash(o)
|
224
236
|
o.each_with_index do |pair, i|
|
data/lib/arel/visitors/mysql.rb
CHANGED
@@ -15,7 +15,9 @@ module Arel # :nodoc: all
|
|
15
15
|
|
16
16
|
###
|
17
17
|
# :'(
|
18
|
-
#
|
18
|
+
# To retrieve all rows from a certain offset up to the end of the result set,
|
19
|
+
# you can use some large number for the second parameter.
|
20
|
+
# https://dev.mysql.com/doc/refman/en/select.html
|
19
21
|
def visit_Arel_Nodes_SelectStatement(o, collector)
|
20
22
|
if o.offset && !o.limit
|
21
23
|
o.limit = Arel::Nodes::Limit.new(18446744073709551615)
|
@@ -48,6 +50,14 @@ module Arel # :nodoc: all
|
|
48
50
|
visit_Arel_Nodes_IsNotDistinctFrom o, collector
|
49
51
|
end
|
50
52
|
|
53
|
+
def visit_Arel_Nodes_Regexp(o, collector)
|
54
|
+
infix_value o, collector, " REGEXP "
|
55
|
+
end
|
56
|
+
|
57
|
+
def visit_Arel_Nodes_NotRegexp(o, collector)
|
58
|
+
infix_value o, collector, " NOT REGEXP "
|
59
|
+
end
|
60
|
+
|
51
61
|
# In the simple case, MySQL allows us to place JOINs directly into the UPDATE
|
52
62
|
# query. However, this does not allow for LIMIT, OFFSET and ORDER. To support
|
53
63
|
# these, we must use a subquery.
|
@@ -41,10 +41,6 @@ module Arel # :nodoc: all
|
|
41
41
|
visit(o.expr, collector) << " )"
|
42
42
|
end
|
43
43
|
|
44
|
-
def visit_Arel_Nodes_BindParam(o, collector)
|
45
|
-
collector.add_bind(o.value) { |i| "$#{i}" }
|
46
|
-
end
|
47
|
-
|
48
44
|
def visit_Arel_Nodes_GroupingElement(o, collector)
|
49
45
|
collector << "( "
|
50
46
|
visit(o.expr, collector) << " )"
|
@@ -82,6 +78,21 @@ module Arel # :nodoc: all
|
|
82
78
|
visit o.right, collector
|
83
79
|
end
|
84
80
|
|
81
|
+
def visit_Arel_Nodes_NullsFirst(o, collector)
|
82
|
+
visit o.expr, collector
|
83
|
+
collector << " NULLS FIRST"
|
84
|
+
end
|
85
|
+
|
86
|
+
def visit_Arel_Nodes_NullsLast(o, collector)
|
87
|
+
visit o.expr, collector
|
88
|
+
collector << " NULLS LAST"
|
89
|
+
end
|
90
|
+
|
91
|
+
BIND_BLOCK = proc { |i| "$#{i}" }
|
92
|
+
private_constant :BIND_BLOCK
|
93
|
+
|
94
|
+
def bind_block; BIND_BLOCK; end
|
95
|
+
|
85
96
|
# Used by Lateral visitor to enclose select queries in parentheses
|
86
97
|
def grouping_parentheses(o, collector)
|
87
98
|
if o.expr.is_a? Nodes::SelectStatement
|