sequel 4.46.0 → 4.49.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG +210 -0
- data/Rakefile +1 -1
- data/doc/advanced_associations.rdoc +1 -1
- data/doc/opening_databases.rdoc +3 -2
- data/doc/release_notes/4.47.0.txt +56 -0
- data/doc/release_notes/4.48.0.txt +293 -0
- data/doc/release_notes/4.49.0.txt +222 -0
- data/lib/sequel/adapters/ado/access.rb +2 -1
- data/lib/sequel/adapters/do/postgres.rb +5 -2
- data/lib/sequel/adapters/ibmdb.rb +30 -8
- data/lib/sequel/adapters/jdbc/as400.rb +1 -1
- data/lib/sequel/adapters/jdbc/db2.rb +12 -3
- data/lib/sequel/adapters/jdbc/derby.rb +4 -5
- data/lib/sequel/adapters/jdbc/h2.rb +10 -1
- data/lib/sequel/adapters/jdbc/oracle.rb +16 -2
- data/lib/sequel/adapters/jdbc/postgresql.rb +46 -20
- data/lib/sequel/adapters/jdbc/sqlanywhere.rb +9 -7
- data/lib/sequel/adapters/jdbc/sqlserver.rb +20 -6
- data/lib/sequel/adapters/jdbc.rb +39 -23
- data/lib/sequel/adapters/mock.rb +27 -19
- data/lib/sequel/adapters/mysql.rb +17 -16
- data/lib/sequel/adapters/mysql2.rb +5 -6
- data/lib/sequel/adapters/oracle.rb +5 -9
- data/lib/sequel/adapters/postgres.rb +91 -103
- data/lib/sequel/adapters/shared/db2.rb +22 -6
- data/lib/sequel/adapters/shared/mssql.rb +5 -4
- data/lib/sequel/adapters/shared/mysql.rb +79 -25
- data/lib/sequel/adapters/shared/oracle.rb +26 -3
- data/lib/sequel/adapters/shared/postgres.rb +199 -95
- data/lib/sequel/adapters/shared/sqlanywhere.rb +23 -10
- data/lib/sequel/adapters/shared/sqlite.rb +72 -82
- data/lib/sequel/adapters/sqlanywhere.rb +4 -1
- data/lib/sequel/adapters/sqlite.rb +5 -3
- data/lib/sequel/adapters/swift/postgres.rb +5 -2
- data/lib/sequel/adapters/tinytds.rb +0 -5
- data/lib/sequel/adapters/utils/mysql_mysql2.rb +1 -1
- data/lib/sequel/adapters/utils/pg_types.rb +2 -76
- data/lib/sequel/ast_transformer.rb +1 -1
- data/lib/sequel/connection_pool/sharded_single.rb +1 -1
- data/lib/sequel/connection_pool/sharded_threaded.rb +1 -1
- data/lib/sequel/connection_pool/single.rb +2 -2
- data/lib/sequel/connection_pool/threaded.rb +2 -2
- data/lib/sequel/connection_pool.rb +9 -2
- data/lib/sequel/core.rb +2 -2
- data/lib/sequel/database/connecting.rb +8 -8
- data/lib/sequel/database/dataset.rb +6 -3
- data/lib/sequel/database/dataset_defaults.rb +14 -1
- data/lib/sequel/database/misc.rb +1 -1
- data/lib/sequel/database/query.rb +3 -0
- data/lib/sequel/database/schema_methods.rb +1 -1
- data/lib/sequel/dataset/actions.rb +72 -10
- data/lib/sequel/dataset/dataset_module.rb +58 -0
- data/lib/sequel/dataset/graph.rb +1 -1
- data/lib/sequel/dataset/misc.rb +1 -0
- data/lib/sequel/dataset/prepared_statements.rb +3 -3
- data/lib/sequel/dataset/query.rb +22 -11
- data/lib/sequel/dataset.rb +1 -1
- data/lib/sequel/exceptions.rb +8 -0
- data/lib/sequel/extensions/_model_pg_row.rb +5 -2
- data/lib/sequel/extensions/core_extensions.rb +4 -1
- data/lib/sequel/extensions/current_datetime_timestamp.rb +2 -1
- data/lib/sequel/extensions/date_arithmetic.rb +1 -0
- data/lib/sequel/extensions/duplicate_columns_handler.rb +3 -3
- data/lib/sequel/extensions/empty_array_ignore_nulls.rb +3 -0
- data/lib/sequel/extensions/filter_having.rb +2 -0
- data/lib/sequel/extensions/freeze_datasets.rb +2 -0
- data/lib/sequel/extensions/from_block.rb +1 -1
- data/lib/sequel/extensions/graph_each.rb +2 -2
- data/lib/sequel/extensions/hash_aliases.rb +2 -0
- data/lib/sequel/extensions/identifier_mangling.rb +0 -7
- data/lib/sequel/extensions/meta_def.rb +2 -0
- data/lib/sequel/extensions/migration.rb +11 -8
- data/lib/sequel/extensions/no_auto_literal_strings.rb +1 -1
- data/lib/sequel/extensions/null_dataset.rb +1 -0
- data/lib/sequel/extensions/pagination.rb +1 -1
- data/lib/sequel/extensions/pg_array.rb +207 -130
- data/lib/sequel/extensions/pg_hstore.rb +38 -20
- data/lib/sequel/extensions/pg_inet.rb +18 -6
- data/lib/sequel/extensions/pg_interval.rb +19 -12
- data/lib/sequel/extensions/pg_json.rb +25 -14
- data/lib/sequel/extensions/pg_json_ops.rb +2 -2
- data/lib/sequel/extensions/pg_range.rb +133 -100
- data/lib/sequel/extensions/pg_range_ops.rb +4 -3
- data/lib/sequel/extensions/pg_row.rb +68 -39
- data/lib/sequel/extensions/pg_row_ops.rb +11 -5
- data/lib/sequel/extensions/query_literals.rb +2 -0
- data/lib/sequel/extensions/ruby18_symbol_extensions.rb +2 -0
- data/lib/sequel/extensions/s.rb +1 -1
- data/lib/sequel/extensions/schema_dumper.rb +29 -25
- data/lib/sequel/extensions/sequel_3_dataset_methods.rb +3 -1
- data/lib/sequel/extensions/sequel_4_dataset_methods.rb +83 -0
- data/lib/sequel/extensions/server_block.rb +32 -15
- data/lib/sequel/extensions/set_overrides.rb +2 -2
- data/lib/sequel/extensions/string_agg.rb +0 -1
- data/lib/sequel/extensions/symbol_aref.rb +0 -4
- data/lib/sequel/model/associations.rb +35 -7
- data/lib/sequel/model/base.rb +113 -87
- data/lib/sequel/model/dataset_module.rb +5 -43
- data/lib/sequel/model/errors.rb +2 -1
- data/lib/sequel/model/inflections.rb +17 -5
- data/lib/sequel/model.rb +26 -58
- data/lib/sequel/plugins/active_model.rb +2 -2
- data/lib/sequel/plugins/association_autoreloading.rb +2 -0
- data/lib/sequel/plugins/association_dependencies.rb +3 -3
- data/lib/sequel/plugins/association_pks.rb +73 -46
- data/lib/sequel/plugins/association_proxies.rb +1 -1
- data/lib/sequel/plugins/auto_validations.rb +6 -2
- data/lib/sequel/plugins/boolean_readers.rb +2 -2
- data/lib/sequel/plugins/boolean_subsets.rb +1 -1
- data/lib/sequel/plugins/caching.rb +19 -13
- data/lib/sequel/plugins/class_table_inheritance.rb +24 -13
- data/lib/sequel/plugins/column_conflicts.rb +7 -2
- data/lib/sequel/plugins/column_select.rb +3 -3
- data/lib/sequel/plugins/composition.rb +2 -2
- data/lib/sequel/plugins/csv_serializer.rb +8 -8
- data/lib/sequel/plugins/dataset_associations.rb +25 -13
- data/lib/sequel/plugins/defaults_setter.rb +13 -1
- data/lib/sequel/plugins/eager_each.rb +1 -1
- data/lib/sequel/plugins/force_encoding.rb +2 -2
- data/lib/sequel/plugins/hook_class_methods.rb +9 -12
- data/lib/sequel/plugins/identifier_columns.rb +2 -0
- data/lib/sequel/plugins/instance_filters.rb +3 -1
- data/lib/sequel/plugins/instance_hooks.rb +17 -9
- data/lib/sequel/plugins/json_serializer.rb +19 -12
- data/lib/sequel/plugins/lazy_attributes.rb +8 -7
- data/lib/sequel/plugins/many_to_one_pk_lookup.rb +2 -0
- data/lib/sequel/plugins/modification_detection.rb +3 -0
- data/lib/sequel/plugins/nested_attributes.rb +6 -2
- data/lib/sequel/plugins/pg_array_associations.rb +5 -0
- data/lib/sequel/plugins/pg_row.rb +4 -2
- data/lib/sequel/plugins/pg_typecast_on_load.rb +2 -0
- data/lib/sequel/plugins/prepared_statements.rb +1 -0
- data/lib/sequel/plugins/rcte_tree.rb +4 -24
- data/lib/sequel/plugins/serialization.rb +9 -15
- data/lib/sequel/plugins/single_table_inheritance.rb +8 -3
- data/lib/sequel/plugins/split_values.rb +6 -5
- data/lib/sequel/plugins/static_cache.rb +31 -25
- data/lib/sequel/plugins/subset_conditions.rb +3 -1
- data/lib/sequel/plugins/table_select.rb +1 -1
- data/lib/sequel/plugins/touch.rb +4 -2
- data/lib/sequel/plugins/validation_class_methods.rb +5 -6
- data/lib/sequel/plugins/validation_helpers.rb +14 -8
- data/lib/sequel/plugins/xml_serializer.rb +4 -4
- data/lib/sequel/sql.rb +18 -9
- data/lib/sequel/version.rb +1 -1
- data/spec/adapters/db2_spec.rb +115 -14
- data/spec/adapters/mssql_spec.rb +4 -4
- data/spec/adapters/mysql_spec.rb +83 -29
- data/spec/adapters/oracle_spec.rb +28 -24
- data/spec/adapters/postgres_spec.rb +40 -24
- data/spec/adapters/sqlanywhere_spec.rb +88 -86
- data/spec/adapters/sqlite_spec.rb +29 -24
- data/spec/bin_spec.rb +7 -1
- data/spec/core/connection_pool_spec.rb +45 -14
- data/spec/core/database_spec.rb +155 -0
- data/spec/core/dataset_spec.rb +219 -36
- data/spec/core/schema_spec.rb +16 -0
- data/spec/core/spec_helper.rb +1 -0
- data/spec/core_extensions_spec.rb +6 -2
- data/spec/extensions/active_model_spec.rb +1 -1
- data/spec/extensions/arbitrary_servers_spec.rb +1 -1
- data/spec/extensions/association_pks_spec.rb +34 -2
- data/spec/extensions/auto_literal_strings_spec.rb +5 -1
- data/spec/extensions/auto_validations_spec.rb +2 -0
- data/spec/extensions/boolean_readers_spec.rb +1 -1
- data/spec/extensions/boolean_subsets_spec.rb +1 -1
- data/spec/extensions/class_table_inheritance_spec.rb +106 -19
- data/spec/extensions/column_conflicts_spec.rb +11 -0
- data/spec/extensions/column_select_spec.rb +1 -0
- data/spec/extensions/composition_spec.rb +13 -0
- data/spec/extensions/connection_validator_spec.rb +1 -1
- data/spec/extensions/dataset_associations_spec.rb +20 -8
- data/spec/extensions/defaults_setter_spec.rb +15 -1
- data/spec/extensions/filter_having_spec.rb +5 -3
- data/spec/extensions/hash_aliases_spec.rb +3 -1
- data/spec/extensions/identifier_columns_spec.rb +3 -1
- data/spec/extensions/implicit_subquery_spec.rb +4 -2
- data/spec/extensions/json_serializer_spec.rb +18 -0
- data/spec/extensions/lazy_attributes_spec.rb +3 -3
- data/spec/extensions/many_through_many_spec.rb +4 -4
- data/spec/extensions/meta_def_spec.rb +9 -0
- data/spec/extensions/migration_spec.rb +3 -3
- data/spec/extensions/nested_attributes_spec.rb +14 -3
- data/spec/extensions/no_auto_literal_strings_spec.rb +8 -4
- data/spec/extensions/null_dataset_spec.rb +1 -1
- data/spec/extensions/pg_array_associations_spec.rb +29 -18
- data/spec/extensions/pg_array_spec.rb +44 -25
- data/spec/extensions/pg_hstore_spec.rb +10 -0
- data/spec/extensions/pg_inet_spec.rb +26 -0
- data/spec/extensions/pg_interval_spec.rb +20 -0
- data/spec/extensions/pg_json_spec.rb +24 -0
- data/spec/extensions/pg_range_spec.rb +98 -14
- data/spec/extensions/pg_row_spec.rb +14 -4
- data/spec/extensions/pg_typecast_on_load_spec.rb +11 -9
- data/spec/extensions/prepared_statements_safe_spec.rb +1 -1
- data/spec/extensions/query_literals_spec.rb +3 -1
- data/spec/extensions/schema_dumper_spec.rb +108 -94
- data/spec/extensions/sequel_3_dataset_methods_spec.rb +10 -6
- data/spec/extensions/sequel_4_dataset_methods_spec.rb +121 -0
- data/spec/extensions/serialization_spec.rb +1 -1
- data/spec/extensions/server_block_spec.rb +7 -0
- data/spec/extensions/single_table_inheritance_spec.rb +17 -1
- data/spec/extensions/spec_helper.rb +7 -1
- data/spec/extensions/static_cache_spec.rb +75 -24
- data/spec/extensions/string_agg_spec.rb +1 -1
- data/spec/extensions/touch_spec.rb +9 -0
- data/spec/extensions/validation_helpers_spec.rb +10 -5
- data/spec/extensions/whitelist_security_spec.rb +26 -0
- data/spec/integration/associations_test.rb +8 -0
- data/spec/integration/dataset_test.rb +45 -44
- data/spec/integration/model_test.rb +53 -4
- data/spec/integration/plugin_test.rb +28 -4
- data/spec/integration/prepared_statement_test.rb +3 -0
- data/spec/integration/schema_test.rb +21 -1
- data/spec/integration/transaction_test.rb +40 -40
- data/spec/model/association_reflection_spec.rb +43 -1
- data/spec/model/associations_spec.rb +29 -9
- data/spec/model/class_dataset_methods_spec.rb +20 -4
- data/spec/model/dataset_methods_spec.rb +12 -3
- data/spec/model/eager_loading_spec.rb +8 -8
- data/spec/model/model_spec.rb +45 -1
- data/spec/model/plugins_spec.rb +34 -0
- data/spec/model/record_spec.rb +1 -1
- data/spec/spec_config.rb +2 -0
- metadata +11 -4
- data/spec/adapters/firebird_spec.rb +0 -405
- data/spec/adapters/informix_spec.rb +0 -100
@@ -40,10 +40,7 @@
|
|
40
40
|
# If you specify the range database type, Sequel will automatically cast
|
41
41
|
# the value to that type when literalizing.
|
42
42
|
#
|
43
|
-
#
|
44
|
-
# probably want to modify the schema parsing/typecasting so that it
|
45
|
-
# recognizes and correctly handles the range type columns, which you can
|
46
|
-
# do by:
|
43
|
+
# To use this extension, load it into the Database instance:
|
47
44
|
#
|
48
45
|
# DB.extension :pg_range
|
49
46
|
#
|
@@ -52,11 +49,10 @@
|
|
52
49
|
#
|
53
50
|
# This extension makes it easy to add support for other range types. In
|
54
51
|
# general, you just need to make sure that the subtype is handled and has the
|
55
|
-
# appropriate converter installed
|
56
|
-
# instance's conversion_procs usingthe appropriate type OID. For user defined
|
52
|
+
# appropriate converter installed. For user defined
|
57
53
|
# types, you can do this via:
|
58
54
|
#
|
59
|
-
# DB.
|
55
|
+
# DB.add_conversion_proc(subtype_oid){|string| }
|
60
56
|
#
|
61
57
|
# Then you can call
|
62
58
|
# Sequel::Postgres::PGRange::DatabaseMethods#register_range_type
|
@@ -66,18 +62,6 @@
|
|
66
62
|
#
|
67
63
|
# DB.register_range_type('timerange')
|
68
64
|
#
|
69
|
-
# You can also register range types on a global basis using
|
70
|
-
# Sequel::Postgres::PGRange.register. In this case, you'll have
|
71
|
-
# to specify the type oids:
|
72
|
-
#
|
73
|
-
# Sequel::Postgres::PG_TYPES[1234] = lambda{|string| }
|
74
|
-
# Sequel::Postgres::PGRange.register('foo', :oid=>4321, :subtype_oid=>1234)
|
75
|
-
#
|
76
|
-
# Both Sequel::Postgres::PGRange::DatabaseMethods#register_range_type
|
77
|
-
# and Sequel::Postgres::PGRange.register support many options to
|
78
|
-
# customize the range type handling. See the Sequel::Postgres::PGRange.register
|
79
|
-
# method documentation.
|
80
|
-
#
|
81
65
|
# This extension integrates with the pg_array extension. If you plan
|
82
66
|
# to use arrays of range types, load the pg_array extension before the
|
83
67
|
# pg_range extension:
|
@@ -86,54 +70,45 @@
|
|
86
70
|
#
|
87
71
|
# Related module: Sequel::Postgres::PGRange
|
88
72
|
|
89
|
-
Sequel.require 'adapters/
|
73
|
+
Sequel.require 'adapters/shared/postgres'
|
90
74
|
|
91
75
|
module Sequel
|
92
76
|
module Postgres
|
93
77
|
class PGRange
|
94
78
|
include Sequel::SQL::AliasMethods
|
95
79
|
|
96
|
-
#
|
97
|
-
# used in the schema parsing.
|
80
|
+
# SEQUEL5: Remove
|
98
81
|
RANGE_TYPES = {}
|
99
82
|
|
100
83
|
EMPTY = 'empty'.freeze
|
84
|
+
Sequel::Deprecation.deprecate_constant(self, :EMPTY)
|
101
85
|
EMPTY_STRING = ''.freeze
|
86
|
+
Sequel::Deprecation.deprecate_constant(self, :EMPTY_STRING)
|
102
87
|
COMMA = ','.freeze
|
88
|
+
Sequel::Deprecation.deprecate_constant(self, :COMMA)
|
103
89
|
QUOTED_EMPTY_STRING = '""'.freeze
|
90
|
+
Sequel::Deprecation.deprecate_constant(self, :QUOTED_EMPTY_STRING)
|
104
91
|
OPEN_PAREN = "(".freeze
|
92
|
+
Sequel::Deprecation.deprecate_constant(self, :OPEN_PAREN)
|
105
93
|
CLOSE_PAREN = ")".freeze
|
94
|
+
Sequel::Deprecation.deprecate_constant(self, :CLOSE_PAREN)
|
106
95
|
OPEN_BRACKET = "[".freeze
|
96
|
+
Sequel::Deprecation.deprecate_constant(self, :OPEN_BRACKET)
|
107
97
|
CLOSE_BRACKET = "]".freeze
|
98
|
+
Sequel::Deprecation.deprecate_constant(self, :CLOSE_BRACKET)
|
108
99
|
ESCAPE_RE = /("|,|\\|\[|\]|\(|\))/.freeze
|
100
|
+
Sequel::Deprecation.deprecate_constant(self, :ESCAPE_RE)
|
109
101
|
ESCAPE_REPLACE = '\\\\\1'.freeze
|
102
|
+
Sequel::Deprecation.deprecate_constant(self, :ESCAPE_REPLACE)
|
110
103
|
CAST = '::'.freeze
|
104
|
+
Sequel::Deprecation.deprecate_constant(self, :CAST)
|
111
105
|
|
112
|
-
#
|
113
|
-
# has been extended with DatabaseMethods recognize the range type given and set up the
|
114
|
-
# appropriate typecasting. Also sets up automatic typecasting for the native postgres
|
115
|
-
# adapter, so that on retrieval, the values are automatically converted to PGRange instances.
|
116
|
-
# The db_type argument should be the name of the range type. Accepts the following options:
|
117
|
-
#
|
118
|
-
# :converter :: A callable object (e.g. Proc), that is called with the start or end of the range
|
119
|
-
# (usually a string), and should return the appropriate typecasted object.
|
120
|
-
# :oid :: The PostgreSQL OID for the range type. This is used by the Sequel postgres adapter
|
121
|
-
# to set up automatic type conversion on retrieval from the database.
|
122
|
-
# :subtype_oid :: Should be the PostgreSQL OID for the range's subtype. If given,
|
123
|
-
# automatically sets the :converter option by looking for scalar conversion
|
124
|
-
# proc.
|
125
|
-
# :type_procs :: A hash mapping oids to conversion procs, used for setting the default :converter
|
126
|
-
# for :subtype_oid. Defaults to the global Sequel::Postgres::PG_TYPES.
|
127
|
-
# :typecast_method_map :: The map in which to place the database type string to type symbol mapping.
|
128
|
-
# Defaults to RANGE_TYPES.
|
129
|
-
# :typecast_methods_module :: If given, a module object to add the typecasting method to. Defaults
|
130
|
-
# to DatabaseMethods.
|
131
|
-
#
|
132
|
-
# If a block is given, it is treated as the :converter option.
|
106
|
+
# SEQUEL5: Remove
|
133
107
|
def self.register(db_type, opts=OPTS, &block)
|
108
|
+
Sequel::Deprecation.deprecate("Sequel::Postgres::PGRange.register", "Use Database#register_range_type on a Database instance using the pg_range extension") unless opts[:skip_deprecation_warning]
|
134
109
|
db_type = db_type.to_s.dup.freeze
|
135
110
|
|
136
|
-
type_procs = opts[:type_procs] ||
|
111
|
+
type_procs = opts[:type_procs] || PG__TYPES
|
137
112
|
mod = opts[:typecast_methods_module] || DatabaseMethods
|
138
113
|
typecast_method_map = opts[:typecast_method_map] || RANGE_TYPES
|
139
114
|
|
@@ -155,14 +130,19 @@ module Sequel
|
|
155
130
|
define_range_typecast_method(mod, db_type, parser)
|
156
131
|
|
157
132
|
if oid = opts[:oid]
|
133
|
+
if opts[:skip_deprecation_warning]
|
134
|
+
def parser.call(s)
|
135
|
+
Sequel::Deprecation.deprecate("Conversion proc for #{db_type} added globally by pg_range extension", "Load the pg_range extension into the Database instance")
|
136
|
+
super
|
137
|
+
end
|
138
|
+
end
|
158
139
|
type_procs[oid] = parser
|
159
140
|
end
|
160
141
|
|
161
142
|
nil
|
162
143
|
end
|
163
144
|
|
164
|
-
#
|
165
|
-
# the parser argument to do the type conversion.
|
145
|
+
# SEQUEL5: Remove
|
166
146
|
def self.define_range_typecast_method(mod, type, parser)
|
167
147
|
mod.class_eval do
|
168
148
|
meth = :"typecast_value_#{type}"
|
@@ -174,12 +154,12 @@ module Sequel
|
|
174
154
|
|
175
155
|
# Creates callable objects that convert strings into PGRange instances.
|
176
156
|
class Parser
|
177
|
-
|
178
|
-
|
179
|
-
PARSER = /\A(\[|\()("((?:\\"|[^"])*)"|[^"]*),("((?:\\"|[^"])*)"|[^"]*)(\]|\))\z/o
|
180
|
-
|
157
|
+
PARSER = /\A(\[|\()("((?:\\"|[^"])*)"|[^"]*),("((?:\\"|[^"])*)"|[^"]*)(\]|\))\z/
|
158
|
+
Sequel::Deprecation.deprecate_constant(self, :PARSER)
|
181
159
|
REPLACE_RE = /\\(.)/.freeze
|
160
|
+
Sequel::Deprecation.deprecate_constant(self, :REPLACE_RE)
|
182
161
|
REPLACE_WITH = '\1'.freeze
|
162
|
+
Sequel::Deprecation.deprecate_constant(self, :REPLACE_WITH)
|
183
163
|
|
184
164
|
# The database range type for this parser (e.g. 'int4range'),
|
185
165
|
# automatically setting the db_type for the returned PGRange instances.
|
@@ -197,11 +177,11 @@ module Sequel
|
|
197
177
|
|
198
178
|
# Parse the range type input string into a PGRange value.
|
199
179
|
def call(string)
|
200
|
-
if string ==
|
180
|
+
if string == 'empty'
|
201
181
|
return PGRange.empty(db_type)
|
202
182
|
end
|
203
183
|
|
204
|
-
raise(InvalidValue, "invalid or unhandled range format: #{string.inspect}") unless matches =
|
184
|
+
raise(InvalidValue, "invalid or unhandled range format: #{string.inspect}") unless matches = /\A(\[|\()("((?:\\"|[^"])*)"|[^"]*),("((?:\\"|[^"])*)"|[^"]*)(\]|\))\z/.match(string)
|
205
185
|
|
206
186
|
exclude_begin = matches[1] == '('
|
207
187
|
exclude_end = matches[6] == ')'
|
@@ -215,12 +195,12 @@ module Sequel
|
|
215
195
|
# to always use the quoted output form when characters need to be escaped, so
|
216
196
|
# there isn't a need to unescape unquoted output.
|
217
197
|
if beg = matches[3]
|
218
|
-
beg.gsub!(
|
198
|
+
beg.gsub!(/\\(.)/, '\1')
|
219
199
|
else
|
220
200
|
beg = matches[2] unless matches[2].empty?
|
221
201
|
end
|
222
202
|
if en = matches[5]
|
223
|
-
en.gsub!(
|
203
|
+
en.gsub!(/\\(.)/, '\1')
|
224
204
|
else
|
225
205
|
en = matches[4] unless matches[4].empty?
|
226
206
|
end
|
@@ -241,20 +221,32 @@ module Sequel
|
|
241
221
|
db.instance_eval do
|
242
222
|
@pg_range_schema_types ||= {}
|
243
223
|
extend_datasets(DatasetMethods)
|
244
|
-
|
224
|
+
register_range_type('int4range', :oid=>3904, :subtype_oid=>23)
|
225
|
+
register_range_type('numrange', :oid=>3906, :subtype_oid=>1700)
|
226
|
+
register_range_type('tsrange', :oid=>3908, :subtype_oid=>1114)
|
227
|
+
register_range_type('tstzrange', :oid=>3910, :subtype_oid=>1184)
|
228
|
+
register_range_type('daterange', :oid=>3912, :subtype_oid=>1082)
|
229
|
+
register_range_type('int8range', :oid=>3926, :subtype_oid=>20)
|
230
|
+
if respond_to?(:register_array_type)
|
231
|
+
register_array_type('int4range', :oid=>3905, :scalar_oid=>3904, :scalar_typecast=>:int4range)
|
232
|
+
register_array_type('numrange', :oid=>3907, :scalar_oid=>3906, :scalar_typecast=>:numrange)
|
233
|
+
register_array_type('tsrange', :oid=>3909, :scalar_oid=>3908, :scalar_typecast=>:tsrange)
|
234
|
+
register_array_type('tstzrange', :oid=>3911, :scalar_oid=>3910, :scalar_typecast=>:tstzrange)
|
235
|
+
register_array_type('daterange', :oid=>3913, :scalar_oid=>3912, :scalar_typecast=>:daterange)
|
236
|
+
register_array_type('int8range', :oid=>3927, :scalar_oid=>3926, :scalar_typecast=>:int8range)
|
237
|
+
end
|
245
238
|
[:int4range, :numrange, :tsrange, :tstzrange, :daterange, :int8range].each do |v|
|
246
239
|
@schema_type_classes[v] = PGRange
|
247
240
|
end
|
248
|
-
end
|
249
241
|
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
255
|
-
|
242
|
+
procs = conversion_procs
|
243
|
+
add_conversion_proc(3908, Parser.new("tsrange", procs[1114]))
|
244
|
+
add_conversion_proc(3910, Parser.new("tstzrange", procs[1184]))
|
245
|
+
if defined?(PGArray::Creator)
|
246
|
+
add_conversion_proc(3909, PGArray::Creator.new("tsrange", procs[3908]))
|
247
|
+
add_conversion_proc(3911, PGArray::Creator.new("tstzrange", procs[3910]))
|
248
|
+
end
|
256
249
|
end
|
257
|
-
|
258
250
|
end
|
259
251
|
|
260
252
|
# Handle Range and PGRange values in bound variables
|
@@ -276,20 +268,62 @@ module Sequel
|
|
276
268
|
end
|
277
269
|
|
278
270
|
# Register a database specific range type. This can be used to support
|
279
|
-
# different range types per Database.
|
280
|
-
#
|
281
|
-
#
|
271
|
+
# different range types per Database. Options:
|
272
|
+
#
|
273
|
+
# :converter :: A callable object (e.g. Proc), that is called with the start or end of the range
|
274
|
+
# (usually a string), and should return the appropriate typecasted object.
|
275
|
+
# :oid :: The PostgreSQL OID for the range type. This is used by the Sequel postgres adapter
|
276
|
+
# to set up automatic type conversion on retrieval from the database.
|
277
|
+
# :subtype_oid :: Should be the PostgreSQL OID for the range's subtype. If given,
|
278
|
+
# automatically sets the :converter option by looking for scalar conversion
|
279
|
+
# proc.
|
280
|
+
#
|
281
|
+
# If a block is given, it is treated as the :converter option.
|
282
282
|
def register_range_type(db_type, opts=OPTS, &block)
|
283
|
-
|
284
|
-
|
283
|
+
oid = opts[:oid]
|
284
|
+
soid = opts[:subtype_oid]
|
285
|
+
|
286
|
+
if has_converter = opts.has_key?(:converter)
|
287
|
+
raise Error, "can't provide both a block and :converter option to register_range_type" if block
|
288
|
+
converter = opts[:converter]
|
289
|
+
else
|
290
|
+
has_converter = true if block
|
291
|
+
converter = block
|
292
|
+
end
|
293
|
+
|
294
|
+
unless (soid || has_converter) && oid
|
285
295
|
range_oid, subtype_oid = from(:pg_range).join(:pg_type, :oid=>:rngtypid).where(:typname=>db_type.to_s).get([:rngtypid, :rngsubtype])
|
286
|
-
|
287
|
-
|
296
|
+
soid ||= subtype_oid unless has_converter
|
297
|
+
oid ||= range_oid
|
298
|
+
end
|
299
|
+
|
300
|
+
db_type = db_type.to_s.dup.freeze
|
301
|
+
|
302
|
+
if converter = opts[:converter]
|
303
|
+
raise Error, "can't provide both a block and :converter option to register" if block
|
304
|
+
else
|
305
|
+
converter = block
|
306
|
+
end
|
307
|
+
|
308
|
+
if soid
|
309
|
+
raise Error, "can't provide both a converter and :subtype_oid option to register" if has_converter
|
310
|
+
raise Error, "no conversion proc for :subtype_oid=>#{soid.inspect} in conversion_procs" unless converter = conversion_procs[soid]
|
311
|
+
end
|
312
|
+
|
313
|
+
parser = Parser.new(db_type, converter)
|
314
|
+
add_conversion_proc(oid, parser)
|
315
|
+
|
316
|
+
@pg_range_schema_types[db_type] = db_type.to_sym
|
317
|
+
|
318
|
+
(class << self; self end).class_eval do
|
319
|
+
meth = :"typecast_value_#{db_type}"
|
320
|
+
define_method(meth){|v| typecast_value_pg_range(v, parser)}
|
321
|
+
private meth
|
288
322
|
end
|
289
323
|
|
290
|
-
PGRange.register(db_type, opts, &block)
|
291
324
|
@schema_type_classes[:"#{opts[:type_symbol] || db_type}"] = PGRange
|
292
|
-
conversion_procs_updated
|
325
|
+
conversion_procs_updated # SEQUEL5: Remove
|
326
|
+
nil
|
293
327
|
end
|
294
328
|
|
295
329
|
private
|
@@ -304,9 +338,7 @@ module Sequel
|
|
304
338
|
end
|
305
339
|
end
|
306
340
|
|
307
|
-
#
|
308
|
-
# they use the database's timezone instead of the global Sequel
|
309
|
-
# timezone.
|
341
|
+
# SEQUEL5: Remove
|
310
342
|
def get_conversion_procs
|
311
343
|
procs = super
|
312
344
|
|
@@ -322,7 +354,7 @@ module Sequel
|
|
322
354
|
|
323
355
|
# Recognize the registered database range types.
|
324
356
|
def schema_column_type(db_type)
|
325
|
-
if type = @pg_range_schema_types[db_type] || RANGE_TYPES[db_type]
|
357
|
+
if type = @pg_range_schema_types[db_type] || RANGE_TYPES[db_type] # SEQUEL5: Remove || RANGE_TYPES[db_type]
|
326
358
|
type
|
327
359
|
else
|
328
360
|
super
|
@@ -490,17 +522,17 @@ module Sequel
|
|
490
522
|
# Append a literalize version of the receiver to the sql.
|
491
523
|
def sql_literal_append(ds, sql)
|
492
524
|
if (s = @db_type) && !empty?
|
493
|
-
sql << s.to_s <<
|
525
|
+
sql << s.to_s << "("
|
494
526
|
ds.literal_append(sql, self.begin)
|
495
|
-
sql <<
|
527
|
+
sql << ','
|
496
528
|
ds.literal_append(sql, self.end)
|
497
|
-
sql <<
|
498
|
-
ds.literal_append(sql, "#{exclude_begin? ?
|
499
|
-
sql <<
|
529
|
+
sql << ','
|
530
|
+
ds.literal_append(sql, "#{exclude_begin? ? "(" : "["}#{exclude_end? ? ")" : "]"}")
|
531
|
+
sql << ")"
|
500
532
|
else
|
501
533
|
ds.literal_append(sql, unquoted_literal(ds))
|
502
534
|
if s
|
503
|
-
sql <<
|
535
|
+
sql << '::' << s.to_s
|
504
536
|
end
|
505
537
|
end
|
506
538
|
end
|
@@ -536,9 +568,9 @@ module Sequel
|
|
536
568
|
# Separated out for use by the bound argument code.
|
537
569
|
def unquoted_literal(ds)
|
538
570
|
if empty?
|
539
|
-
|
571
|
+
'empty'
|
540
572
|
else
|
541
|
-
"#{exclude_begin? ?
|
573
|
+
"#{exclude_begin? ? "(" : "["}#{escape_value(self.begin, ds)},#{escape_value(self.end, ds)}#{exclude_end? ? ")" : "]"}"
|
542
574
|
end
|
543
575
|
end
|
544
576
|
|
@@ -549,7 +581,7 @@ module Sequel
|
|
549
581
|
def escape_value(k, ds)
|
550
582
|
case k
|
551
583
|
when nil
|
552
|
-
|
584
|
+
''
|
553
585
|
when Date, Time
|
554
586
|
ds.literal(k)[1...-1]
|
555
587
|
when Integer, Float
|
@@ -560,29 +592,30 @@ module Sequel
|
|
560
592
|
k
|
561
593
|
when String
|
562
594
|
if k.empty?
|
563
|
-
|
595
|
+
'""'
|
564
596
|
else
|
565
|
-
k.gsub(
|
597
|
+
k.gsub(/("|,|\\|\[|\]|\(|\))/, '\\\\\1')
|
566
598
|
end
|
567
599
|
else
|
568
|
-
ds.literal(k).gsub(
|
600
|
+
ds.literal(k).gsub(/("|,|\\|\[|\]|\(|\))/, '\\\\\1')
|
569
601
|
end
|
570
602
|
end
|
571
603
|
end
|
572
604
|
|
573
|
-
|
574
|
-
PGRange.register('
|
575
|
-
PGRange.register('
|
576
|
-
PGRange.register('
|
577
|
-
PGRange.register('
|
578
|
-
PGRange.register('
|
605
|
+
# SEQUEL5: Remove
|
606
|
+
PGRange.register('int4range', :oid=>3904, :subtype_oid=>23, :skip_deprecation_warning=>true)
|
607
|
+
PGRange.register('numrange', :oid=>3906, :subtype_oid=>1700, :skip_deprecation_warning=>true)
|
608
|
+
PGRange.register('tsrange', :oid=>3908, :subtype_oid=>1114, :skip_deprecation_warning=>true)
|
609
|
+
PGRange.register('tstzrange', :oid=>3910, :subtype_oid=>1184, :skip_deprecation_warning=>true)
|
610
|
+
PGRange.register('daterange', :oid=>3912, :subtype_oid=>1082, :skip_deprecation_warning=>true)
|
611
|
+
PGRange.register('int8range', :oid=>3926, :subtype_oid=>20, :skip_deprecation_warning=>true)
|
579
612
|
if defined?(PGArray) && PGArray.respond_to?(:register)
|
580
|
-
PGArray.register('int4range', :oid=>3905, :scalar_oid=>3904, :scalar_typecast=>:int4range)
|
581
|
-
PGArray.register('numrange', :oid=>3907, :scalar_oid=>3906, :scalar_typecast=>:numrange)
|
582
|
-
PGArray.register('tsrange', :oid=>3909, :scalar_oid=>3908, :scalar_typecast=>:tsrange)
|
583
|
-
PGArray.register('tstzrange', :oid=>3911, :scalar_oid=>3910, :scalar_typecast=>:tstzrange)
|
584
|
-
PGArray.register('daterange', :oid=>3913, :scalar_oid=>3912, :scalar_typecast=>:daterange)
|
585
|
-
PGArray.register('int8range', :oid=>3927, :scalar_oid=>3926, :scalar_typecast=>:int8range)
|
613
|
+
PGArray.register('int4range', :oid=>3905, :scalar_oid=>3904, :scalar_typecast=>:int4range, :skip_deprecation_warning=>true)
|
614
|
+
PGArray.register('numrange', :oid=>3907, :scalar_oid=>3906, :scalar_typecast=>:numrange, :skip_deprecation_warning=>true)
|
615
|
+
PGArray.register('tsrange', :oid=>3909, :scalar_oid=>3908, :scalar_typecast=>:tsrange, :skip_deprecation_warning=>true)
|
616
|
+
PGArray.register('tstzrange', :oid=>3911, :scalar_oid=>3910, :scalar_typecast=>:tstzrange, :skip_deprecation_warning=>true)
|
617
|
+
PGArray.register('daterange', :oid=>3913, :scalar_oid=>3912, :scalar_typecast=>:daterange, :skip_deprecation_warning=>true)
|
618
|
+
PGArray.register('int8range', :oid=>3927, :scalar_oid=>3926, :scalar_typecast=>:int8range, :skip_deprecation_warning=>true)
|
586
619
|
end
|
587
620
|
end
|
588
621
|
|
@@ -75,13 +75,14 @@ module Sequel
|
|
75
75
|
:starts_after => ["(".freeze, " &> ".freeze, ")".freeze].freeze,
|
76
76
|
:adjacent_to => ["(".freeze, " -|- ".freeze, ")".freeze].freeze,
|
77
77
|
:overlaps => ["(".freeze, " && ".freeze, ")".freeze].freeze,
|
78
|
-
}
|
78
|
+
}#.freeze # SEQUEL5
|
79
79
|
FUNCTIONS = %w'lower upper isempty lower_inc upper_inc lower_inf upper_inf'
|
80
|
+
Sequel::Deprecation.deprecate_constant(self, :FUNCTIONS)
|
80
81
|
|
81
|
-
|
82
|
+
%w'lower upper isempty lower_inc upper_inc lower_inf upper_inf'.each do |f|
|
82
83
|
class_eval("def #{f}; function(:#{f}) end", __FILE__, __LINE__)
|
83
84
|
end
|
84
|
-
OPERATORS.
|
85
|
+
OPERATORS.each_key do |f|
|
85
86
|
class_eval("def #{f}(v); operator(:#{f}, v) end", __FILE__, __LINE__)
|
86
87
|
end
|
87
88
|
|