torque-postgresql 4.0.0 → 4.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Rakefile +24 -0
- data/lib/torque/postgresql/adapter/database_statements.rb +89 -7
- data/lib/torque/postgresql/adapter/inheritance_statements.rb +297 -0
- data/lib/torque/postgresql/adapter/oid/array.rb +17 -0
- data/lib/torque/postgresql/adapter/oid/box.rb +1 -1
- data/lib/torque/postgresql/adapter/oid/circle.rb +1 -1
- data/lib/torque/postgresql/adapter/oid/composite.rb +116 -0
- data/lib/torque/postgresql/adapter/oid/line.rb +1 -1
- data/lib/torque/postgresql/adapter/oid/lquery.rb +53 -0
- data/lib/torque/postgresql/adapter/oid/ltree.rb +53 -0
- data/lib/torque/postgresql/adapter/oid/segment.rb +1 -1
- data/lib/torque/postgresql/adapter/oid/struct.rb +150 -0
- data/lib/torque/postgresql/adapter/oid/struct_list.rb +52 -0
- data/lib/torque/postgresql/adapter/oid/struct_set.rb +38 -0
- data/lib/torque/postgresql/adapter/quoting.rb +11 -2
- data/lib/torque/postgresql/adapter/schema_definitions.rb +46 -0
- data/lib/torque/postgresql/adapter/schema_dumper.rb +28 -2
- data/lib/torque/postgresql/adapter/schema_statements.rb +207 -0
- data/lib/torque/postgresql/adapter.rb +2 -5
- data/lib/torque/postgresql/arel/nodes.rb +63 -1
- data/lib/torque/postgresql/arel/visitors.rb +19 -8
- data/lib/torque/postgresql/associations/join_dependency.rb +55 -0
- data/lib/torque/postgresql/associations.rb +3 -0
- data/lib/torque/postgresql/attributes/base.rb +94 -0
- data/lib/torque/postgresql/attributes/composite.rb +102 -0
- data/lib/torque/postgresql/attributes/enum.rb +13 -2
- data/lib/torque/postgresql/attributes/lquery.rb +180 -0
- data/lib/torque/postgresql/attributes/ltree.rb +169 -0
- data/lib/torque/postgresql/attributes/simple_enum.rb +72 -0
- data/lib/torque/postgresql/attributes/struct.rb +137 -0
- data/lib/torque/postgresql/base.rb +17 -14
- data/lib/torque/postgresql/config.rb +81 -14
- data/lib/torque/postgresql/inheritance/expander.rb +66 -0
- data/lib/torque/postgresql/inheritance/record.rb +52 -0
- data/lib/torque/postgresql/inheritance.rb +138 -65
- data/lib/torque/postgresql/migration/command_recorder.rb +76 -0
- data/lib/torque/postgresql/predicate_builder/composite_handler.rb +109 -0
- data/lib/torque/postgresql/predicate_builder/ltree_handler.rb +44 -0
- data/lib/torque/postgresql/predicate_builder/struct_handler.rb +68 -0
- data/lib/torque/postgresql/predicate_builder.rb +26 -0
- data/lib/torque/postgresql/predicate_table.rb +61 -0
- data/lib/torque/postgresql/railtie.rb +35 -0
- data/lib/torque/postgresql/relation/inheritance.rb +146 -28
- data/lib/torque/postgresql/relation/join_series.rb +8 -6
- data/lib/torque/postgresql/relation/merger.rb +23 -7
- data/lib/torque/postgresql/relation.rb +12 -11
- data/lib/torque/postgresql/schema_cache.rb +1 -0
- data/lib/torque/postgresql/validations.rb +29 -0
- data/lib/torque/postgresql/version.rb +1 -1
- data/lib/torque/postgresql/versioned_commands/command_migration.rb +1 -1
- data/lib/torque/postgresql.rb +6 -0
- data/spec/initialize.rb +20 -2
- data/spec/mocks/cache_query.rb +12 -0
- data/spec/models/author.rb +1 -1
- data/spec/models/comment.rb +2 -0
- data/spec/models/place.rb +2 -0
- data/spec/models/profile.rb +31 -0
- data/spec/schema.rb +34 -4
- data/spec/tests/arel_spec.rb +5 -3
- data/spec/tests/composite_spec.rb +800 -0
- data/spec/tests/ltree_spec.rb +552 -0
- data/spec/tests/struct_spec.rb +968 -0
- data/spec/tests/table_inheritance_spec.rb +1027 -56
- metadata +49 -7
|
@@ -35,7 +35,7 @@ module Torque
|
|
|
35
35
|
|
|
36
36
|
# Merge auxiliary statements activated by +with+
|
|
37
37
|
def merge_auxiliary_statements
|
|
38
|
-
return unless relation.is_a?(Relation::AuxiliaryStatement)
|
|
38
|
+
return unless defined?(Relation::AuxiliaryStatement) && relation.is_a?(Relation::AuxiliaryStatement)
|
|
39
39
|
return if other.auxiliary_statements_values.blank?
|
|
40
40
|
|
|
41
41
|
current = relation.auxiliary_statements_values.map{ |cte| cte.class }
|
|
@@ -46,21 +46,37 @@ module Torque
|
|
|
46
46
|
end
|
|
47
47
|
end
|
|
48
48
|
|
|
49
|
-
# Merge settings related to inheritance tables
|
|
49
|
+
# Merge settings related to inheritance tables, going through the
|
|
50
|
+
# public operations so that their conflicts are still detected
|
|
50
51
|
def merge_inheritance
|
|
51
52
|
return unless relation.is_a?(Relation::Inheritance)
|
|
52
53
|
|
|
53
|
-
relation.
|
|
54
|
+
relation.itself_only! if other.itself_only_value.present?
|
|
54
55
|
|
|
55
|
-
if other.
|
|
56
|
-
|
|
57
|
-
|
|
56
|
+
return if other.expand_records_values.blank?
|
|
57
|
+
|
|
58
|
+
if relation.model == other.model
|
|
59
|
+
types = (relation.expand_records_values + other.expand_records_values).uniq
|
|
60
|
+
relation.expand_records!(*types, eager_load: other.expand_records_eager_load_value)
|
|
61
|
+
else
|
|
62
|
+
raise_eager_load_conflict! if other.expand_records_eager_load_value
|
|
63
|
+
|
|
64
|
+
relation.expand_records_scoped_value = relation.expand_records_scoped_value
|
|
65
|
+
.merge(other.model => other.expand_records_values) { |_, a, b| (a + b).uniq }
|
|
58
66
|
end
|
|
59
67
|
end
|
|
60
68
|
|
|
69
|
+
def raise_eager_load_conflict!
|
|
70
|
+
raise InheritanceError.new(<<~MSG.squish)
|
|
71
|
+
Expanding the records of a different model happens through a
|
|
72
|
+
preload, which has no query to eager load the inherited tables
|
|
73
|
+
into, so the two cannot be merged.
|
|
74
|
+
MSG
|
|
75
|
+
end
|
|
76
|
+
|
|
61
77
|
# Merge settings related to buckets
|
|
62
78
|
def merge_buckets
|
|
63
|
-
return unless relation.is_a?(Relation::Buckets)
|
|
79
|
+
return unless defined?(Relation::Buckets) && relation.is_a?(Relation::Buckets)
|
|
64
80
|
return if other.buckets_value.blank?
|
|
65
81
|
|
|
66
82
|
relation.buckets_value = other.buckets_value
|
|
@@ -13,9 +13,9 @@ module Torque
|
|
|
13
13
|
include DistinctOn
|
|
14
14
|
include Inheritance
|
|
15
15
|
|
|
16
|
-
SINGLE_VALUE_METHODS = %i[itself_only buckets]
|
|
16
|
+
SINGLE_VALUE_METHODS = %i[itself_only buckets expand_records_eager_load expand_records_scoped]
|
|
17
17
|
MULTI_VALUE_METHODS = %i[
|
|
18
|
-
select_extra distinct_on auxiliary_statements
|
|
18
|
+
select_extra distinct_on auxiliary_statements expand_records
|
|
19
19
|
]
|
|
20
20
|
|
|
21
21
|
VALUE_METHODS = SINGLE_VALUE_METHODS + MULTI_VALUE_METHODS
|
|
@@ -76,7 +76,8 @@ module Torque
|
|
|
76
76
|
return unless relation
|
|
77
77
|
|
|
78
78
|
table = predicate_builder.send(:table)
|
|
79
|
-
|
|
79
|
+
associated = AR810 ? table.associated_with(relation.to_s) : table.associated_with?(relation.to_s)
|
|
80
|
+
if associated
|
|
80
81
|
table.associated_table(relation.to_s).send(:klass)
|
|
81
82
|
else
|
|
82
83
|
raise ArgumentError, "Relation for #{relation} not found on #{klass}"
|
|
@@ -87,7 +88,7 @@ module Torque
|
|
|
87
88
|
# the given column
|
|
88
89
|
def cast_for_condition(column, value)
|
|
89
90
|
column = columns_hash[column.to_s] unless column.is_a?(ARColumn)
|
|
90
|
-
caster = connection.
|
|
91
|
+
caster = connection.lookup_cast_type_for_column(column)
|
|
91
92
|
connection.type_cast(caster.serialize(value))
|
|
92
93
|
end
|
|
93
94
|
|
|
@@ -107,11 +108,10 @@ module Torque
|
|
|
107
108
|
.inheritance.record_class_column_name.to_sym
|
|
108
109
|
end
|
|
109
110
|
|
|
110
|
-
#
|
|
111
|
-
#
|
|
112
|
-
def
|
|
113
|
-
@@
|
|
114
|
-
.inheritance.auto_cast_column_name.to_sym
|
|
111
|
+
# The same name as a string, which is how it arrives on every single
|
|
112
|
+
# row that has to be discriminated
|
|
113
|
+
def _record_class_column_name
|
|
114
|
+
@@record_class_column_name ||= _record_class_attribute.to_s.freeze
|
|
115
115
|
end
|
|
116
116
|
end
|
|
117
117
|
|
|
@@ -138,12 +138,13 @@ module Torque
|
|
|
138
138
|
# the operation of ActiveRecord Relation
|
|
139
139
|
ActiveRecord::Relation.include Relation
|
|
140
140
|
ActiveRecord::Relation.prepend Relation::Initializer
|
|
141
|
+
ActiveRecord::Relation.prepend Relation::Inheritance::Expansion
|
|
141
142
|
|
|
142
143
|
ActiveRecord::Relation::SINGLE_VALUE_METHODS.concat(Relation::SINGLE_VALUE_METHODS)
|
|
143
144
|
ActiveRecord::Relation::MULTI_VALUE_METHODS.concat(Relation::MULTI_VALUE_METHODS)
|
|
144
145
|
ActiveRecord::Relation::VALUE_METHODS.concat(Relation::VALUE_METHODS)
|
|
145
|
-
ActiveRecord::QueryMethods::VALID_UNSCOPING_VALUES.merge(%i[
|
|
146
|
-
distinct_on auxiliary_statements buckets])
|
|
146
|
+
ActiveRecord::QueryMethods::VALID_UNSCOPING_VALUES.merge(%i[expand_records itself_only
|
|
147
|
+
expand_records_eager_load expand_records_scoped distinct_on auxiliary_statements buckets])
|
|
147
148
|
|
|
148
149
|
end
|
|
149
150
|
end
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Torque
|
|
4
|
+
module PostgreSQL
|
|
5
|
+
module Validations
|
|
6
|
+
|
|
7
|
+
# Checks if the objects nested into an attribute are valid, adding a
|
|
8
|
+
# single error to the attribute when any of them is not. It takes the
|
|
9
|
+
# regular +allow_nil+ and +allow_blank+ options, which is how values that
|
|
10
|
+
# are merely absent are left out of it
|
|
11
|
+
#
|
|
12
|
+
# Example:
|
|
13
|
+
# validates :home, nested: true
|
|
14
|
+
# validates :settings, nested: true, allow_blank: true
|
|
15
|
+
class NestedValidator < ActiveModel::EachValidator
|
|
16
|
+
def validate_each(record, attribute, value)
|
|
17
|
+
invalid = Array.wrap(value).any? do |item|
|
|
18
|
+
item.respond_to?(:invalid?) && item.invalid?
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
record.errors.add(attribute, :invalid) if invalid
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
::ActiveRecord::Base.include(Validations)
|
|
28
|
+
end
|
|
29
|
+
end
|
|
@@ -62,7 +62,7 @@ module Torque
|
|
|
62
62
|
end
|
|
63
63
|
end
|
|
64
64
|
|
|
65
|
-
CommandMigration = Struct.new(*%i[filename version op type object_name op_version scope]) do
|
|
65
|
+
CommandMigration = ::Struct.new(*%i[filename version op type object_name op_version scope]) do
|
|
66
66
|
delegate :execute, to: '@migration'
|
|
67
67
|
|
|
68
68
|
def initialize(filename, *args)
|
data/lib/torque/postgresql.rb
CHANGED
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
require 'i18n'
|
|
2
2
|
require 'ostruct'
|
|
3
|
+
require 'monitor'
|
|
3
4
|
require 'active_model'
|
|
4
5
|
require 'active_record'
|
|
5
6
|
require 'active_support'
|
|
6
7
|
|
|
8
|
+
require 'active_support/ordered_options'
|
|
7
9
|
require 'active_support/core_ext/date/acts_like'
|
|
8
10
|
require 'active_support/core_ext/time/zones'
|
|
9
11
|
require 'active_record/connection_adapters/postgresql_adapter'
|
|
@@ -12,6 +14,9 @@ require 'torque/postgresql/config'
|
|
|
12
14
|
require 'torque/postgresql/version'
|
|
13
15
|
require 'torque/postgresql/collector'
|
|
14
16
|
require 'torque/postgresql/geometry_builder'
|
|
17
|
+
require 'torque/postgresql/attributes/ltree'
|
|
18
|
+
require 'torque/postgresql/attributes/lquery'
|
|
19
|
+
require 'torque/postgresql/predicate_table'
|
|
15
20
|
require 'torque/postgresql/predicate_builder'
|
|
16
21
|
|
|
17
22
|
require 'torque/postgresql/i18n'
|
|
@@ -29,5 +34,6 @@ require 'torque/postgresql/reflection'
|
|
|
29
34
|
require 'torque/postgresql/schema_cache'
|
|
30
35
|
require 'torque/postgresql/table_name'
|
|
31
36
|
require 'torque/postgresql/function'
|
|
37
|
+
require 'torque/postgresql/validations'
|
|
32
38
|
|
|
33
39
|
require 'torque/postgresql/railtie' if defined?(Rails)
|
data/spec/initialize.rb
CHANGED
|
@@ -4,15 +4,23 @@ require_relative '../lib/torque/postgresql/adapter/schema_overrides'
|
|
|
4
4
|
|
|
5
5
|
require_relative '../lib/torque/postgresql/adapter/oid/box'
|
|
6
6
|
require_relative '../lib/torque/postgresql/adapter/oid/circle'
|
|
7
|
+
require_relative '../lib/torque/postgresql/adapter/oid/composite'
|
|
7
8
|
require_relative '../lib/torque/postgresql/adapter/oid/enum'
|
|
8
9
|
require_relative '../lib/torque/postgresql/adapter/oid/enum_set'
|
|
9
10
|
require_relative '../lib/torque/postgresql/adapter/oid/interval'
|
|
10
11
|
require_relative '../lib/torque/postgresql/adapter/oid/line'
|
|
12
|
+
require_relative '../lib/torque/postgresql/adapter/oid/lquery'
|
|
13
|
+
require_relative '../lib/torque/postgresql/adapter/oid/ltree'
|
|
11
14
|
require_relative '../lib/torque/postgresql/adapter/oid/segment'
|
|
15
|
+
require_relative '../lib/torque/postgresql/adapter/oid/struct'
|
|
16
|
+
require_relative '../lib/torque/postgresql/adapter/oid/struct_list'
|
|
17
|
+
require_relative '../lib/torque/postgresql/adapter/oid/struct_set'
|
|
12
18
|
|
|
19
|
+
require_relative '../lib/torque/postgresql/attributes/composite'
|
|
13
20
|
require_relative '../lib/torque/postgresql/attributes/enum'
|
|
14
21
|
require_relative '../lib/torque/postgresql/attributes/enum_set'
|
|
15
22
|
require_relative '../lib/torque/postgresql/attributes/period'
|
|
23
|
+
require_relative '../lib/torque/postgresql/attributes/struct'
|
|
16
24
|
require_relative '../lib/torque/postgresql/attributes/full_text_search'
|
|
17
25
|
|
|
18
26
|
require_relative '../lib/torque/postgresql/relation/auxiliary_statement'
|
|
@@ -28,6 +36,7 @@ module Torque
|
|
|
28
36
|
Attributes::Enum.include_on(ActiveRecord::Base)
|
|
29
37
|
Attributes::EnumSet.include_on(ActiveRecord::Base)
|
|
30
38
|
Attributes::Period.include_on(ActiveRecord::Base)
|
|
39
|
+
Attributes::Struct.include_on(ActiveRecord::Base)
|
|
31
40
|
Attributes::FullTextSearch.include_on(ActiveRecord::Base)
|
|
32
41
|
|
|
33
42
|
Relation.include(Relation::AuxiliaryStatement)
|
|
@@ -40,6 +49,11 @@ module Torque
|
|
|
40
49
|
::Object.const_set('TorqueCTE', AuxiliaryStatement)
|
|
41
50
|
::Object.const_set('TorqueRecursiveCTE', AuxiliaryStatement::Recursive)
|
|
42
51
|
|
|
52
|
+
config.composite.namespace = ::Object.const_set('Composite', Module.new)
|
|
53
|
+
config.composite.namespace.define_singleton_method(:const_missing) do |name|
|
|
54
|
+
Attributes::Composite.lookup(name)
|
|
55
|
+
end
|
|
56
|
+
|
|
43
57
|
config.enum.namespace = ::Object.const_set('Enum', Module.new)
|
|
44
58
|
config.enum.namespace.define_singleton_method(:const_missing) do |name|
|
|
45
59
|
Attributes::Enum.lookup(name)
|
|
@@ -50,8 +64,9 @@ module Torque
|
|
|
50
64
|
end
|
|
51
65
|
|
|
52
66
|
ar_type = ActiveRecord::Type
|
|
53
|
-
ar_type.register(:enum,
|
|
54
|
-
ar_type.register(:enum_set,
|
|
67
|
+
ar_type.register(:enum, Adapter::OID::Enum, adapter: :postgresql)
|
|
68
|
+
ar_type.register(:enum_set, Adapter::OID::EnumSet, adapter: :postgresql)
|
|
69
|
+
ar_type.register(:composite, Adapter::OID::Composite, adapter: :postgresql)
|
|
55
70
|
|
|
56
71
|
ar_type.register(:box, Adapter::OID::Box, adapter: :postgresql)
|
|
57
72
|
ar_type.register(:circle, Adapter::OID::Circle, adapter: :postgresql)
|
|
@@ -60,6 +75,9 @@ module Torque
|
|
|
60
75
|
|
|
61
76
|
ar_type.register(:interval, Adapter::OID::Interval, adapter: :postgresql)
|
|
62
77
|
|
|
78
|
+
ar_type.register(:ltree, Adapter::OID::Ltree, adapter: :postgresql)
|
|
79
|
+
ar_type.register(:lquery, Adapter::OID::Lquery, adapter: :postgresql)
|
|
80
|
+
|
|
63
81
|
Arel.build_operations(config.arel.infix_operators)
|
|
64
82
|
|
|
65
83
|
ActiveRecord::Base.connection.torque_load_additional_types
|
data/spec/mocks/cache_query.rb
CHANGED
|
@@ -15,6 +15,18 @@ module Mocks
|
|
|
15
15
|
result
|
|
16
16
|
end
|
|
17
17
|
|
|
18
|
+
def capture_executed_queries
|
|
19
|
+
queries = []
|
|
20
|
+
subscriber = ActiveSupport::Notifications.subscribe('sql.active_record') do |*, payload|
|
|
21
|
+
queries << payload[:sql] unless payload[:name] == 'SCHEMA' || payload[:cached]
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
yield
|
|
25
|
+
queries
|
|
26
|
+
ensure
|
|
27
|
+
ActiveSupport::Notifications.unsubscribe(subscriber)
|
|
28
|
+
end
|
|
29
|
+
|
|
18
30
|
def get_query_with_binds(&block)
|
|
19
31
|
result = nil
|
|
20
32
|
|
data/spec/models/author.rb
CHANGED
data/spec/models/comment.rb
CHANGED
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
class Profile < ActiveRecord::Base
|
|
2
|
+
class Settings < Torque::PostgreSQL::Attributes::Struct
|
|
3
|
+
attribute :theme, :string, default: 'light'
|
|
4
|
+
attribute :notifications, :boolean, default: true
|
|
5
|
+
attribute :tags
|
|
6
|
+
|
|
7
|
+
validates :theme, inclusion: { in: %w[light dark] }, allow_nil: true
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
class Bio < Torque::PostgreSQL::Attributes::Struct
|
|
11
|
+
attribute :headline, :string
|
|
12
|
+
attribute :website, :string
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
class Preview < Torque::PostgreSQL::Attributes::Struct
|
|
16
|
+
attribute :label, :string
|
|
17
|
+
attribute :url, :string
|
|
18
|
+
|
|
19
|
+
validates :url, presence: true
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
class Snippet < Torque::PostgreSQL::Attributes::Struct
|
|
23
|
+
attribute :title, :string
|
|
24
|
+
attribute :body, :string
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
struct_for :settings, Settings, delegate: %i[theme]
|
|
28
|
+
struct_for :bio, Bio
|
|
29
|
+
struct_for :previews, Preview, array: true
|
|
30
|
+
struct_for :snippets, Snippet
|
|
31
|
+
end
|
data/spec/schema.rb
CHANGED
|
@@ -10,13 +10,11 @@
|
|
|
10
10
|
#
|
|
11
11
|
# It's strongly recommended that you check this file into your version control system.
|
|
12
12
|
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
return if ActiveRecord::Migrator.current_version == version
|
|
16
|
-
ActiveRecord::Schema.define(version: version) do
|
|
13
|
+
ActiveRecord::Schema.define do
|
|
17
14
|
self.verbose = false
|
|
18
15
|
|
|
19
16
|
# These are extensions that must be enabled in order to support this database
|
|
17
|
+
enable_extension "ltree"
|
|
20
18
|
enable_extension "pgcrypto"
|
|
21
19
|
enable_extension "plpgsql"
|
|
22
20
|
|
|
@@ -31,6 +29,27 @@ ActiveRecord::Schema.define(version: version) do
|
|
|
31
29
|
create_enum "conflicts", ["valid", "invalid", "untrusted"]
|
|
32
30
|
create_enum "types", ["A", "B", "C", "D"]
|
|
33
31
|
|
|
32
|
+
create_composite_type "address", force: :cascade do |t|
|
|
33
|
+
t.string "street"
|
|
34
|
+
t.string "city"
|
|
35
|
+
t.integer "number"
|
|
36
|
+
t.enum "category", enum_type: :types
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
create_composite_type "full_address", force: :cascade do |t|
|
|
40
|
+
t.composite "base", composite_type: :address
|
|
41
|
+
t.string "country"
|
|
42
|
+
t.date "since"
|
|
43
|
+
t.decimal "rate", precision: 8, scale: 2
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
create_table "places", force: :cascade do |t|
|
|
47
|
+
t.string "name"
|
|
48
|
+
t.composite "home", composite_type: :address
|
|
49
|
+
t.composite "offices", composite_type: :address, array: true
|
|
50
|
+
t.composite "location", composite_type: :full_address
|
|
51
|
+
end
|
|
52
|
+
|
|
34
53
|
create_table "geometries", force: :cascade do |t|
|
|
35
54
|
t.point "point"
|
|
36
55
|
t.line "line"
|
|
@@ -65,6 +84,14 @@ ActiveRecord::Schema.define(version: version) do
|
|
|
65
84
|
t.datetime "updated_at", null: false
|
|
66
85
|
end
|
|
67
86
|
|
|
87
|
+
create_table "profiles", force: :cascade do |t|
|
|
88
|
+
t.string "name"
|
|
89
|
+
t.jsonb "settings"
|
|
90
|
+
t.json "bio"
|
|
91
|
+
t.jsonb "previews"
|
|
92
|
+
t.jsonb "snippets", array: true
|
|
93
|
+
end
|
|
94
|
+
|
|
68
95
|
create_table "authors", force: :cascade do |t|
|
|
69
96
|
t.string "name"
|
|
70
97
|
t.string "type"
|
|
@@ -74,6 +101,7 @@ ActiveRecord::Schema.define(version: version) do
|
|
|
74
101
|
create_table "categories", force: :cascade do |t|
|
|
75
102
|
t.integer "parent_id"
|
|
76
103
|
t.string "title"
|
|
104
|
+
t.ltree "path", index: { using: :gist }
|
|
77
105
|
end
|
|
78
106
|
|
|
79
107
|
create_table "texts", force: :cascade do |t|
|
|
@@ -99,6 +127,7 @@ ActiveRecord::Schema.define(version: version) do
|
|
|
99
127
|
t.enum "types", enum_type: :types, array: true
|
|
100
128
|
t.search_language "lang", null: false, default: 'english'
|
|
101
129
|
t.search_vector "search_vector", columns: :title, language: :lang
|
|
130
|
+
t.tsvector "unhandled"
|
|
102
131
|
t.datetime "created_at", null: false
|
|
103
132
|
t.datetime "updated_at", null: false
|
|
104
133
|
end
|
|
@@ -127,6 +156,7 @@ ActiveRecord::Schema.define(version: version) do
|
|
|
127
156
|
create_table "users", force: :cascade do |t|
|
|
128
157
|
t.string "name", null: false
|
|
129
158
|
t.enum "role", enum_type: :roles, default: :visitor
|
|
159
|
+
t.ltree "permissions", array: true
|
|
130
160
|
t.integer "age"
|
|
131
161
|
t.datetime "created_at", null: false
|
|
132
162
|
t.datetime "updated_at", null: false
|
data/spec/tests/arel_spec.rb
CHANGED
|
@@ -56,7 +56,9 @@ RSpec.describe 'Arel' do
|
|
|
56
56
|
it 'does not break the change column default value method' do
|
|
57
57
|
connection.add_column(:authors, :enabled, :boolean)
|
|
58
58
|
expect { connection.change_column_default(:authors, :enabled, { from: nil, to: true }) }.not_to raise_error
|
|
59
|
-
|
|
59
|
+
# Rails 8.1 type casts column defaults, so it is no longer a string
|
|
60
|
+
expected = Torque::PostgreSQL::AR810 ? true : 'true'
|
|
61
|
+
expect(Author.columns_hash['enabled'].default).to eq(expected)
|
|
60
62
|
end
|
|
61
63
|
|
|
62
64
|
it 'does not break jsonb' do
|
|
@@ -145,12 +147,12 @@ RSpec.describe 'Arel' do
|
|
|
145
147
|
condition = Video.arel_table[:tag_ids].contains([1,2]).cast(:bigint, :array)
|
|
146
148
|
query = Video.all.where(condition).to_sql
|
|
147
149
|
|
|
148
|
-
expect(query).to include(
|
|
150
|
+
expect(query).to include(%{WHERE "videos"."tag_ids" @> '{1,2}'::bigint[]})
|
|
149
151
|
|
|
150
152
|
condition = QuestionSelect.arel_table[:options].overlaps(%w[a b]).cast(:string, :array)
|
|
151
153
|
query = QuestionSelect.all.where(condition).to_sql
|
|
152
154
|
|
|
153
|
-
expect(query).to include(
|
|
155
|
+
expect(query).to include(%{"options" && '{a,b}'::string[]})
|
|
154
156
|
end
|
|
155
157
|
end
|
|
156
158
|
end
|