sequel 5.40.0 → 5.41.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/CHANGELOG +12 -0
- data/MIT-LICENSE +1 -1
- data/doc/release_notes/5.41.0.txt +25 -0
- data/doc/sql.rdoc +1 -1
- data/lib/sequel/adapters/shared/postgres.rb +4 -2
- data/lib/sequel/extensions/blank.rb +2 -0
- data/lib/sequel/extensions/date_arithmetic.rb +4 -8
- data/lib/sequel/extensions/inflector.rb +2 -0
- data/lib/sequel/extensions/named_timezones.rb +5 -1
- data/lib/sequel/extensions/pg_interval.rb +12 -2
- data/lib/sequel/model/associations.rb +28 -5
- data/lib/sequel/plugins/auto_validations.rb +15 -1
- data/lib/sequel/plugins/validation_helpers.rb +6 -2
- data/lib/sequel/version.rb +1 -1
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b0886ae2f4e4f4490b56ced6137e2d849cac2458119d6e67d9a756328336ece6
|
4
|
+
data.tar.gz: 9c4946c8ca82b2b1c99ee9065bef0aa81175128564cd7ab0c0405bd4e682b339
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: aa61ea3a0cb3d0e3ab021d27589e10250ed9d9d5a0b4bf314729d55661624161cabffe9c87278761890a900949756e185ce1f263bf742d9b317f2621a1f75c09
|
7
|
+
data.tar.gz: a8253ea1f6e77b592eb40de7b2544b7b34ff8cd02a79e4dfe5bb26b796dd80d49f052e307590af71fb67b292bc9b9c1def8f400eea0977fdb0d85928a6e9f181
|
data/CHANGELOG
CHANGED
@@ -1,3 +1,15 @@
|
|
1
|
+
=== 5.41.0 (2021-02-01)
|
2
|
+
|
3
|
+
* Have explicit :text option for a String column take priority over :size option on PostgreSQL (jeremyevans) (#1750)
|
4
|
+
|
5
|
+
* Support a :skip_invalid option in auto_validations plugin for not adding errors to a column that already has an error (jeremyevans)
|
6
|
+
|
7
|
+
* Support a :skip_invalid option in validation_helpers for not adding an error to a column that already has an error (jeremyevans)
|
8
|
+
|
9
|
+
* Support :adder, :remover, and :clearer association options that use keyword arguments in Ruby 2.7+ (jeremyevans)
|
10
|
+
|
11
|
+
* Make pg_interval use the same number of seconds per year and per month as ActiveSupport::Duration when using ActiveSupport 5.1+ (jeremyevans)
|
12
|
+
|
1
13
|
=== 5.40.0 (2021-01-01)
|
2
14
|
|
3
15
|
* Support UPDATE FROM syntax in SQLite 3.33.0+ (jeremyevans)
|
data/MIT-LICENSE
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
Copyright (c) 2007-2008 Sharon Rosner
|
2
|
-
Copyright (c) 2008-
|
2
|
+
Copyright (c) 2008-2021 Jeremy Evans
|
3
3
|
|
4
4
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
5
5
|
of this software and associated documentation files (the "Software"), to
|
@@ -0,0 +1,25 @@
|
|
1
|
+
= New Features
|
2
|
+
|
3
|
+
* The validation methods added by the validation_helpers plugin now
|
4
|
+
support the :skip_invalid option, which will not add a validation
|
5
|
+
error on a column if it already has a validation error. This can
|
6
|
+
be useful if you want to avoid having duplicate errors.
|
7
|
+
|
8
|
+
* The auto_validations plugin now supports a :skip_invalid plugin
|
9
|
+
option, which will pass the :skip_invalid option when calling
|
10
|
+
validation methods.
|
11
|
+
|
12
|
+
= Other Improvements
|
13
|
+
|
14
|
+
* The :adder, :remover, and :clearer association options now
|
15
|
+
support keyword arguments in Ruby 2.7+.
|
16
|
+
|
17
|
+
* In the pg_interval extension, Sequel now uses the same number of
|
18
|
+
seconds per month and seconds per year as active_support. It
|
19
|
+
originally used the same number, but active_support changed the
|
20
|
+
values in active_support 5.1. Sequel now uses the active_support
|
21
|
+
values if they are available.
|
22
|
+
|
23
|
+
* When adding a String column on PostgreSQL, an explicit text: true
|
24
|
+
option now takes precedence over an explicit :size option, as it
|
25
|
+
does in Sequel's default behavior.
|
data/doc/sql.rdoc
CHANGED
@@ -544,7 +544,7 @@ On some databases, you can specify null ordering:
|
|
544
544
|
|
545
545
|
=== All Columns (.*)
|
546
546
|
|
547
|
-
To select all columns in a table, Sequel supports the * method on identifiers and qualified without an argument:
|
547
|
+
To select all columns in a table, Sequel supports the * method on identifiers and qualified identifiers without an argument:
|
548
548
|
|
549
549
|
Sequel[:table].* # "table".*
|
550
550
|
Sequel[:schema][:table].* # "schema"."table".*
|
@@ -1500,9 +1500,11 @@ module Sequel
|
|
1500
1500
|
# disallowed or there is a size specified, use the varchar type.
|
1501
1501
|
# Otherwise use the text type.
|
1502
1502
|
def type_literal_generic_string(column)
|
1503
|
-
if column[:
|
1503
|
+
if column[:text]
|
1504
|
+
:text
|
1505
|
+
elsif column[:fixed]
|
1504
1506
|
"char(#{column[:size]||255})"
|
1505
|
-
elsif column[:text] == false
|
1507
|
+
elsif column[:text] == false || column[:size]
|
1506
1508
|
"varchar(#{column[:size]||255})"
|
1507
1509
|
else
|
1508
1510
|
:text
|
@@ -52,14 +52,10 @@ module Sequel
|
|
52
52
|
if defined?(ActiveSupport::Duration) && interval.is_a?(ActiveSupport::Duration)
|
53
53
|
interval = interval.parts
|
54
54
|
end
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
else
|
60
|
-
-interval
|
61
|
-
end
|
62
|
-
DateAdd.new(expr, interval, opts)
|
55
|
+
parts = {}
|
56
|
+
interval.each{|k,v| parts[k] = -v unless v.nil?}
|
57
|
+
parts
|
58
|
+
DateAdd.new(expr, parts, opts)
|
63
59
|
end
|
64
60
|
end
|
65
61
|
|
@@ -107,9 +107,11 @@ class String
|
|
107
107
|
end
|
108
108
|
|
109
109
|
%w'classify constantize dasherize demodulize foreign_key humanize pluralize singularize tableize underscore'.each do |m|
|
110
|
+
# :nocov:
|
110
111
|
if method_defined?(m)
|
111
112
|
alias_method(m, m)
|
112
113
|
end
|
114
|
+
# :nocov:
|
113
115
|
end
|
114
116
|
|
115
117
|
# By default, camelize converts the string to UpperCamelCase. If the argument to camelize
|
@@ -84,9 +84,9 @@ module Sequel
|
|
84
84
|
def convert_output_time_other(v, output_timezone)
|
85
85
|
Time.at(v.to_i, :in => output_timezone)
|
86
86
|
end
|
87
|
-
else
|
88
87
|
# :nodoc:
|
89
88
|
# :nocov:
|
89
|
+
else
|
90
90
|
def convert_input_time_other(v, input_timezone)
|
91
91
|
local_offset = input_timezone.period_for_local(v, &tzinfo_disambiguator_for(v)).utc_total_offset
|
92
92
|
Time.new(1970, 1, 1, 0, 0, 0, local_offset) + v.to_i
|
@@ -105,6 +105,8 @@ module Sequel
|
|
105
105
|
Time.new(1970, 1, 1, 0, 0, 0, local_offset) + v.to_i
|
106
106
|
end
|
107
107
|
end
|
108
|
+
# :nodoc:
|
109
|
+
# :nocov:
|
108
110
|
end
|
109
111
|
|
110
112
|
# Handle both TZInfo 1 and TZInfo 2
|
@@ -142,6 +144,8 @@ module Sequel
|
|
142
144
|
# Convert timezone offset from UTC to the offset for the output_timezone
|
143
145
|
(v - local_offset).new_offset(local_offset)
|
144
146
|
end
|
147
|
+
# :nodoc:
|
148
|
+
# :nocov:
|
145
149
|
end
|
146
150
|
|
147
151
|
# Returns TZInfo::Timezone instance if given a String.
|
@@ -71,6 +71,16 @@ module Sequel
|
|
71
71
|
# Whether ActiveSupport::Duration.new takes parts as array instead of hash
|
72
72
|
USE_PARTS_ARRAY = !defined?(ActiveSupport::VERSION::STRING) || ActiveSupport::VERSION::STRING < '5.1'
|
73
73
|
|
74
|
+
if defined?(ActiveSupport::Duration::SECONDS_PER_MONTH)
|
75
|
+
SECONDS_PER_MONTH = ActiveSupport::Duration::SECONDS_PER_MONTH
|
76
|
+
SECONDS_PER_YEAR = ActiveSupport::Duration::SECONDS_PER_YEAR
|
77
|
+
# :nocov:
|
78
|
+
else
|
79
|
+
SECONDS_PER_MONTH = 2592000
|
80
|
+
SECONDS_PER_YEAR = 31557600
|
81
|
+
# :nocov:
|
82
|
+
end
|
83
|
+
|
74
84
|
# Parse the interval input string into an ActiveSupport::Duration instance.
|
75
85
|
def call(string)
|
76
86
|
raise(InvalidValue, "invalid or unhandled interval format: #{string.inspect}") unless matches = /\A([+-]?\d+ years?\s?)?([+-]?\d+ mons?\s?)?([+-]?\d+ days?\s?)?(?:(?:([+-])?(\d{2,10}):(\d\d):(\d\d(\.\d+)?))|([+-]?\d+ hours?\s?)?([+-]?\d+ mins?\s?)?([+-]?\d+(\.\d+)? secs?\s?)?)?\z/.match(string)
|
@@ -80,12 +90,12 @@ module Sequel
|
|
80
90
|
|
81
91
|
if v = matches[1]
|
82
92
|
v = v.to_i
|
83
|
-
value +=
|
93
|
+
value += SECONDS_PER_YEAR * v
|
84
94
|
parts[:years] = v
|
85
95
|
end
|
86
96
|
if v = matches[2]
|
87
97
|
v = v.to_i
|
88
|
-
value +=
|
98
|
+
value += SECONDS_PER_MONTH * v
|
89
99
|
parts[:months] = v
|
90
100
|
end
|
91
101
|
if v = matches[3]
|
@@ -1929,8 +1929,22 @@ module Sequel
|
|
1929
1929
|
# can be easily overridden in the class itself while allowing for
|
1930
1930
|
# super to be called.
|
1931
1931
|
def association_module_def(name, opts=OPTS, &block)
|
1932
|
-
association_module(opts)
|
1933
|
-
|
1932
|
+
mod = association_module(opts)
|
1933
|
+
mod.send(:define_method, name, &block)
|
1934
|
+
mod.send(:alias_method, name, name)
|
1935
|
+
end
|
1936
|
+
|
1937
|
+
# Add a method to the module included in the class, so the method
|
1938
|
+
# can be easily overridden in the class itself while allowing for
|
1939
|
+
# super to be called. This method allows passing keywords through
|
1940
|
+
# the defined methods.
|
1941
|
+
def association_module_delegate_def(name, opts, &block)
|
1942
|
+
mod = association_module(opts)
|
1943
|
+
mod.send(:define_method, name, &block)
|
1944
|
+
# :nocov:
|
1945
|
+
mod.send(:ruby2_keywords, name) if mod.respond_to?(:ruby2_keywords, true)
|
1946
|
+
# :nocov:
|
1947
|
+
mod.send(:alias_method, name, name)
|
1934
1948
|
end
|
1935
1949
|
|
1936
1950
|
# Add a private method to the module included in the class.
|
@@ -1982,17 +1996,17 @@ module Sequel
|
|
1982
1996
|
|
1983
1997
|
if adder = opts[:adder]
|
1984
1998
|
association_module_private_def(opts[:_add_method], opts, &adder)
|
1985
|
-
|
1999
|
+
association_module_delegate_def(opts[:add_method], opts){|o,*args| add_associated_object(opts, o, *args)}
|
1986
2000
|
end
|
1987
2001
|
|
1988
2002
|
if remover = opts[:remover]
|
1989
2003
|
association_module_private_def(opts[:_remove_method], opts, &remover)
|
1990
|
-
|
2004
|
+
association_module_delegate_def(opts[:remove_method], opts){|o,*args| remove_associated_object(opts, o, *args)}
|
1991
2005
|
end
|
1992
2006
|
|
1993
2007
|
if clearer = opts[:clearer]
|
1994
2008
|
association_module_private_def(opts[:_remove_all_method], opts, &clearer)
|
1995
|
-
|
2009
|
+
association_module_delegate_def(opts[:remove_all_method], opts){|*args| remove_all_associated_objects(opts, *args)}
|
1996
2010
|
end
|
1997
2011
|
end
|
1998
2012
|
|
@@ -2424,6 +2438,9 @@ module Sequel
|
|
2424
2438
|
run_association_callbacks(opts, :after_add, o)
|
2425
2439
|
o
|
2426
2440
|
end
|
2441
|
+
# :nocov:
|
2442
|
+
ruby2_keywords(:add_associated_object) if respond_to?(:ruby2_keywords, true)
|
2443
|
+
# :nocov:
|
2427
2444
|
|
2428
2445
|
# Add/Set the current object to/as the given object's reciprocal association.
|
2429
2446
|
def add_reciprocal_object(opts, o)
|
@@ -2566,6 +2583,9 @@ module Sequel
|
|
2566
2583
|
associations[opts[:name]] = []
|
2567
2584
|
ret
|
2568
2585
|
end
|
2586
|
+
# :nocov:
|
2587
|
+
ruby2_keywords(:remove_all_associated_objects) if respond_to?(:ruby2_keywords, true)
|
2588
|
+
# :nocov:
|
2569
2589
|
|
2570
2590
|
# Remove the given associated object from the given association
|
2571
2591
|
def remove_associated_object(opts, o, *args)
|
@@ -2587,6 +2607,9 @@ module Sequel
|
|
2587
2607
|
run_association_callbacks(opts, :after_remove, o)
|
2588
2608
|
o
|
2589
2609
|
end
|
2610
|
+
# :nocov:
|
2611
|
+
ruby2_keywords(:remove_associated_object) if respond_to?(:ruby2_keywords, true)
|
2612
|
+
# :nocov:
|
2590
2613
|
|
2591
2614
|
# Check that the object from the associated table specified by the primary key
|
2592
2615
|
# is currently associated to the receiver. If it is associated, return the object, otherwise
|
@@ -14,7 +14,9 @@ module Sequel
|
|
14
14
|
# the plugin looks at the database schema for the model's table. To determine
|
15
15
|
# the unique validations, Sequel looks at the indexes on the table. In order
|
16
16
|
# for this plugin to be fully functional, the underlying database adapter needs
|
17
|
-
# to support both schema and index parsing.
|
17
|
+
# to support both schema and index parsing. Additionally, unique validations are
|
18
|
+
# only added for models that select from a simple table, they are not added for models
|
19
|
+
# that select from a subquery or joined dataset.
|
18
20
|
#
|
19
21
|
# This plugin uses the validation_helpers plugin underneath to implement the
|
20
22
|
# validations. It does not allow for any per-column validation message
|
@@ -51,6 +53,11 @@ module Sequel
|
|
51
53
|
# This works for unique_opts, max_length_opts, schema_types_opts,
|
52
54
|
# explicit_not_null_opts, and not_null_opts.
|
53
55
|
#
|
56
|
+
# If you only want auto_validations to add validations to columns that do not already
|
57
|
+
# have an error associated with them, you can use the skip_invalid option:
|
58
|
+
#
|
59
|
+
# Model.plugin :auto_validations, skip_invalid: true
|
60
|
+
#
|
54
61
|
# Usage:
|
55
62
|
#
|
56
63
|
# # Make all model subclass use auto validations (called before loading subclasses)
|
@@ -100,6 +107,13 @@ module Sequel
|
|
100
107
|
h[type] = h[type].merge(type_opts).freeze
|
101
108
|
end
|
102
109
|
end
|
110
|
+
|
111
|
+
if opts[:skip_invalid]
|
112
|
+
[:not_null, :explicit_not_null, :max_length, :schema_types].each do |type|
|
113
|
+
h[type] = h[type].merge(:skip_invalid=>true).freeze
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
103
117
|
@auto_validate_options = h.freeze
|
104
118
|
end
|
105
119
|
end
|
@@ -36,6 +36,7 @@ module Sequel
|
|
36
36
|
# :message :: The message to use. Can be a string which is used directly, or a
|
37
37
|
# proc which is called. If the validation method takes a argument before the array of attributes,
|
38
38
|
# that argument is passed as an argument to the proc.
|
39
|
+
# :skip_invalid :: Do not try to validate columns that are already invalid.
|
39
40
|
#
|
40
41
|
# The default validation options for all models can be modified by
|
41
42
|
# overridding the Model#default_validation_helpers_options private method.
|
@@ -281,14 +282,17 @@ module Sequel
|
|
281
282
|
DEFAULT_OPTIONS[type]
|
282
283
|
end
|
283
284
|
|
284
|
-
# Skip validating any attribute that matches one of the allow_* options
|
285
|
+
# Skip validating any attribute that matches one of the allow_* options,
|
286
|
+
# or already has an error if the skip_invalid option is given.
|
287
|
+
#
|
285
288
|
# Otherwise, yield the attribute, value, and passed option :message to
|
286
289
|
# the block. If the block returns anything except nil or false, add it as
|
287
290
|
# an error message for that attributes.
|
288
291
|
def validatable_attributes(atts, opts)
|
289
|
-
am, an, ab, m = opts.values_at(:allow_missing, :allow_nil, :allow_blank, :message)
|
292
|
+
am, an, ab, m, si = opts.values_at(:allow_missing, :allow_nil, :allow_blank, :message, :skip_invalid)
|
290
293
|
from_values = opts[:from] == :values
|
291
294
|
Array(atts).each do |a|
|
295
|
+
next if si && errors.on(a)
|
292
296
|
next if am && !values.has_key?(a)
|
293
297
|
v = from_values ? values[a] : get_column_value(a)
|
294
298
|
next if an && v.nil?
|
data/lib/sequel/version.rb
CHANGED
@@ -6,7 +6,7 @@ module Sequel
|
|
6
6
|
|
7
7
|
# The minor version of Sequel. Bumped for every non-patch level
|
8
8
|
# release, generally around once a month.
|
9
|
-
MINOR =
|
9
|
+
MINOR = 41
|
10
10
|
|
11
11
|
# The tiny version of Sequel. Usually 0, only bumped for bugfix
|
12
12
|
# releases that fix regressions from previous versions.
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: sequel
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 5.
|
4
|
+
version: 5.41.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jeremy Evans
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-
|
11
|
+
date: 2021-02-01 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: minitest
|
@@ -184,6 +184,7 @@ extra_rdoc_files:
|
|
184
184
|
- doc/release_notes/5.39.0.txt
|
185
185
|
- doc/release_notes/5.4.0.txt
|
186
186
|
- doc/release_notes/5.40.0.txt
|
187
|
+
- doc/release_notes/5.41.0.txt
|
187
188
|
- doc/release_notes/5.5.0.txt
|
188
189
|
- doc/release_notes/5.6.0.txt
|
189
190
|
- doc/release_notes/5.7.0.txt
|
@@ -252,6 +253,7 @@ files:
|
|
252
253
|
- doc/release_notes/5.39.0.txt
|
253
254
|
- doc/release_notes/5.4.0.txt
|
254
255
|
- doc/release_notes/5.40.0.txt
|
256
|
+
- doc/release_notes/5.41.0.txt
|
255
257
|
- doc/release_notes/5.5.0.txt
|
256
258
|
- doc/release_notes/5.6.0.txt
|
257
259
|
- doc/release_notes/5.7.0.txt
|