sequel 4.44.0 → 4.45.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (140) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG +110 -0
  3. data/README.rdoc +8 -9
  4. data/doc/active_record.rdoc +2 -3
  5. data/doc/model_plugins.rdoc +1 -1
  6. data/doc/opening_databases.rdoc +0 -46
  7. data/doc/release_notes/4.45.0.txt +370 -0
  8. data/lib/sequel/adapters/cubrid.rb +2 -0
  9. data/lib/sequel/adapters/do.rb +2 -0
  10. data/lib/sequel/adapters/jdbc/as400.rb +2 -0
  11. data/lib/sequel/adapters/jdbc/cubrid.rb +2 -0
  12. data/lib/sequel/adapters/jdbc/firebirdsql.rb +2 -0
  13. data/lib/sequel/adapters/jdbc/informix-sqli.rb +2 -0
  14. data/lib/sequel/adapters/jdbc/jdbcprogress.rb +2 -0
  15. data/lib/sequel/adapters/jdbc/mysql.rb +1 -0
  16. data/lib/sequel/adapters/jdbc/postgresql.rb +5 -0
  17. data/lib/sequel/adapters/mysql.rb +1 -0
  18. data/lib/sequel/adapters/mysql2.rb +1 -0
  19. data/lib/sequel/adapters/odbc/oracle.rb +11 -0
  20. data/lib/sequel/adapters/odbc/progress.rb +2 -0
  21. data/lib/sequel/adapters/postgres.rb +0 -2
  22. data/lib/sequel/adapters/shared/cubrid.rb +2 -0
  23. data/lib/sequel/adapters/shared/firebird.rb +2 -0
  24. data/lib/sequel/adapters/shared/informix.rb +2 -0
  25. data/lib/sequel/adapters/shared/mssql.rb +47 -7
  26. data/lib/sequel/adapters/shared/mysql.rb +16 -1
  27. data/lib/sequel/adapters/shared/postgres.rb +9 -1
  28. data/lib/sequel/adapters/shared/progress.rb +2 -0
  29. data/lib/sequel/adapters/shared/sqlanywhere.rb +1 -1
  30. data/lib/sequel/adapters/swift.rb +2 -0
  31. data/lib/sequel/ast_transformer.rb +13 -6
  32. data/lib/sequel/core.rb +13 -16
  33. data/lib/sequel/database/connecting.rb +25 -10
  34. data/lib/sequel/database/dataset.rb +6 -1
  35. data/lib/sequel/database/dataset_defaults.rb +9 -2
  36. data/lib/sequel/database/misc.rb +10 -3
  37. data/lib/sequel/database/schema_methods.rb +4 -0
  38. data/lib/sequel/dataset/mutation.rb +8 -20
  39. data/lib/sequel/dataset/prepared_statements.rb +2 -0
  40. data/lib/sequel/dataset/query.rb +32 -7
  41. data/lib/sequel/dataset/sql.rb +13 -3
  42. data/lib/sequel/deprecated.rb +9 -1
  43. data/lib/sequel/exceptions.rb +37 -8
  44. data/lib/sequel/extensions/_deprecated_identifier_mangling.rb +117 -0
  45. data/lib/sequel/extensions/date_arithmetic.rb +1 -0
  46. data/lib/sequel/extensions/identifier_mangling.rb +3 -2
  47. data/lib/sequel/extensions/pg_hstore.rb +1 -5
  48. data/lib/sequel/extensions/schema_dumper.rb +3 -1
  49. data/lib/sequel/extensions/sequel_3_dataset_methods.rb +2 -2
  50. data/lib/sequel/extensions/string_agg.rb +1 -0
  51. data/lib/sequel/model.rb +23 -10
  52. data/lib/sequel/model/associations.rb +17 -5
  53. data/lib/sequel/model/base.rb +115 -62
  54. data/lib/sequel/model/dataset_module.rb +10 -3
  55. data/lib/sequel/model/exceptions.rb +7 -5
  56. data/lib/sequel/plugins/association_pks.rb +13 -1
  57. data/lib/sequel/plugins/association_proxies.rb +8 -1
  58. data/lib/sequel/plugins/before_after_save.rb +1 -0
  59. data/lib/sequel/plugins/class_table_inheritance.rb +7 -3
  60. data/lib/sequel/plugins/columns_updated.rb +42 -0
  61. data/lib/sequel/plugins/composition.rb +10 -5
  62. data/lib/sequel/plugins/error_splitter.rb +1 -1
  63. data/lib/sequel/plugins/hook_class_methods.rb +39 -5
  64. data/lib/sequel/plugins/instance_hooks.rb +58 -5
  65. data/lib/sequel/plugins/lazy_attributes.rb +10 -5
  66. data/lib/sequel/plugins/nested_attributes.rb +10 -5
  67. data/lib/sequel/plugins/prepared_statements.rb +7 -0
  68. data/lib/sequel/plugins/prepared_statements_associations.rb +2 -0
  69. data/lib/sequel/plugins/prepared_statements_with_pk.rb +2 -0
  70. data/lib/sequel/plugins/schema.rb +2 -0
  71. data/lib/sequel/plugins/scissors.rb +2 -0
  72. data/lib/sequel/plugins/serialization.rb +10 -5
  73. data/lib/sequel/plugins/split_values.rb +5 -1
  74. data/lib/sequel/plugins/static_cache.rb +2 -2
  75. data/lib/sequel/plugins/tactical_eager_loading.rb +1 -1
  76. data/lib/sequel/plugins/validation_contexts.rb +49 -0
  77. data/lib/sequel/plugins/validation_helpers.rb +1 -0
  78. data/lib/sequel/sql.rb +1 -1
  79. data/lib/sequel/version.rb +1 -1
  80. data/spec/adapters/mssql_spec.rb +31 -0
  81. data/spec/adapters/mysql_spec.rb +20 -2
  82. data/spec/adapters/postgres_spec.rb +43 -12
  83. data/spec/adapters/spec_helper.rb +5 -8
  84. data/spec/core/database_spec.rb +47 -12
  85. data/spec/core/dataset_mutation_spec.rb +22 -22
  86. data/spec/core/dataset_spec.rb +88 -20
  87. data/spec/core/deprecated_spec.rb +1 -1
  88. data/spec/core/expression_filters_spec.rb +1 -1
  89. data/spec/core/mock_adapter_spec.rb +0 -3
  90. data/spec/core/placeholder_literalizer_spec.rb +1 -1
  91. data/spec/core/schema_spec.rb +8 -1
  92. data/spec/core/spec_helper.rb +6 -1
  93. data/spec/core_extensions_spec.rb +4 -0
  94. data/spec/deprecation_helper.rb +17 -0
  95. data/spec/extensions/_deprecated_identifier_mangling_spec.rb +314 -0
  96. data/spec/extensions/association_pks_spec.rb +61 -13
  97. data/spec/extensions/association_proxies_spec.rb +3 -3
  98. data/spec/extensions/class_table_inheritance_spec.rb +39 -0
  99. data/spec/extensions/columns_updated_spec.rb +35 -0
  100. data/spec/extensions/composition_spec.rb +6 -1
  101. data/spec/extensions/hook_class_methods_spec.rb +114 -26
  102. data/spec/extensions/identifier_mangling_spec.rb +107 -73
  103. data/spec/extensions/instance_hooks_spec.rb +78 -14
  104. data/spec/extensions/lazy_attributes_spec.rb +8 -2
  105. data/spec/extensions/many_through_many_spec.rb +2 -2
  106. data/spec/extensions/mssql_optimistic_locking_spec.rb +1 -1
  107. data/spec/extensions/nested_attributes_spec.rb +8 -2
  108. data/spec/extensions/pg_array_spec.rb +18 -4
  109. data/spec/extensions/prepared_statements_associations_spec.rb +48 -39
  110. data/spec/extensions/prepared_statements_with_pk_spec.rb +13 -11
  111. data/spec/extensions/query_spec.rb +1 -1
  112. data/spec/extensions/schema_dumper_spec.rb +34 -6
  113. data/spec/extensions/schema_spec.rb +13 -7
  114. data/spec/extensions/scissors_spec.rb +3 -1
  115. data/spec/extensions/sequel_3_dataset_methods_spec.rb +4 -4
  116. data/spec/extensions/serialization_spec.rb +7 -1
  117. data/spec/extensions/set_overrides_spec.rb +2 -2
  118. data/spec/extensions/shared_caching_spec.rb +19 -15
  119. data/spec/extensions/spec_helper.rb +7 -3
  120. data/spec/extensions/split_values_spec.rb +45 -10
  121. data/spec/extensions/string_agg_spec.rb +2 -2
  122. data/spec/extensions/subset_conditions_spec.rb +3 -3
  123. data/spec/extensions/tactical_eager_loading_spec.rb +1 -1
  124. data/spec/extensions/validation_contexts_spec.rb +31 -0
  125. data/spec/guards_helper.rb +2 -0
  126. data/spec/integration/associations_test.rb +22 -20
  127. data/spec/integration/dataset_test.rb +25 -2
  128. data/spec/integration/model_test.rb +1 -1
  129. data/spec/integration/plugin_test.rb +11 -16
  130. data/spec/integration/prepared_statement_test.rb +40 -32
  131. data/spec/integration/spec_helper.rb +5 -8
  132. data/spec/model/association_reflection_spec.rb +4 -0
  133. data/spec/model/associations_spec.rb +37 -10
  134. data/spec/model/base_spec.rb +6 -0
  135. data/spec/model/hooks_spec.rb +56 -35
  136. data/spec/model/model_spec.rb +21 -5
  137. data/spec/model/record_spec.rb +14 -11
  138. data/spec/model/spec_helper.rb +7 -1
  139. data/spec/sequel_warning.rb +11 -0
  140. metadata +13 -3
@@ -24,6 +24,9 @@ module Sequel
24
24
  # with all of these modules.
25
25
  attr_reader :dataset_method_modules
26
26
 
27
+ # The Module subclass to use for dataset_module blocks.
28
+ attr_reader :dataset_module_class
29
+
27
30
  # The default options to use for Model#set_fields. These are merged with
28
31
  # the options given to set_fields.
29
32
  attr_accessor :default_set_fields_options
@@ -82,7 +85,7 @@ module Sequel
82
85
  #
83
86
  # or:
84
87
  #
85
- # Foo = Sequel::Model()
88
+ # Foo = Class.new(Sequel::Model)
86
89
  # Foo.set_dataset :my_foo
87
90
  attr_accessor :require_valid_table
88
91
 
@@ -116,7 +119,7 @@ module Sequel
116
119
  # Whether to enable the after_commit and after_rollback hooks when saving/destroying
117
120
  # instances. On by default, can be turned off for performance reasons or when using
118
121
  # prepared transactions (which aren't compatible with after commit/rollback).
119
- attr_accessor :use_after_commit_rollback
122
+ attr_accessor :use_after_commit_rollback # SEQUEL5: Deprecate after release
120
123
 
121
124
  # Whether to use a transaction by default when saving/deleting records (default: true).
122
125
  # If you are sending database queries in before_* or after_* hooks, you shouldn't change
@@ -167,7 +170,9 @@ module Sequel
167
170
  # The purpose of this method is to set the dataset/database automatically
168
171
  # for a model class, if the table name doesn't match the implicit
169
172
  # name. This is neater than using set_dataset inside the class,
170
- # doesn't require a bogus query for the schema.
173
+ # doesn't require a bogus query for the schema, and works when using
174
+ # +require_valid_table+, or with plugins that assume a model's dataset
175
+ # is valid.
171
176
  #
172
177
  # When creating subclasses of Sequel::Model itself, this method is usually
173
178
  # called on Sequel itself, using <tt>Sequel::Model(:something)</tt>.
@@ -188,10 +193,8 @@ module Sequel
188
193
  # end
189
194
  def Model(source)
190
195
  if cache_anonymous_models
191
- mutex = @Model_mutex
192
- cache = mutex.synchronize{@Model_cache ||= {}}
193
-
194
- if klass = mutex.synchronize{cache[source]}
196
+ cache = Sequel.synchronize{@Model_cache ||= {}}
197
+ if klass = Sequel.synchronize{cache[source]}
195
198
  return klass
196
199
  end
197
200
  end
@@ -205,12 +208,24 @@ module Sequel
205
208
  end
206
209
 
207
210
  if cache_anonymous_models
208
- mutex.synchronize{cache[source] = klass}
211
+ Sequel.synchronize{cache[source] = klass}
209
212
  end
210
213
 
211
214
  klass
212
215
  end
213
216
 
217
+ def initialize_copy(_)
218
+ Sequel::Deprecation.deprecate("Model.clone", "Create a subclass of the model instead of cloning it.")
219
+ # raise(Error, "cannot dup/clone a Sequel::Model class") # SEQUEL5
220
+ super
221
+ end
222
+ def dup
223
+ Sequel::Deprecation.deprecate("Model.dup", "Create a subclass of the model instead of duping it.")
224
+ # raise(Error, "cannot dup/clone a Sequel::Model class") # SEQUEL5
225
+ super
226
+ end
227
+
228
+
214
229
  # Returns the first record from the database matching the conditions.
215
230
  # If a hash is given, it is used as the conditions. If another
216
231
  # object is given, it finds the first record whose primary key(s) match
@@ -338,13 +353,13 @@ module Sequel
338
353
  dataset_extend(mod)
339
354
  mod
340
355
  else
341
- @dataset_module ||= DatasetModule.new(self)
356
+ @dataset_module ||= dataset_module_class.new(self)
342
357
  @dataset_module.module_eval(&Proc.new) if block_given?
343
358
  dataset_extend(@dataset_module)
344
359
  @dataset_module
345
360
  end
346
361
  end
347
-
362
+
348
363
  # Returns the database associated with the Model class.
349
364
  # If this model doesn't have a database associated with it,
350
365
  # assumes the superclass's database, or the first object in
@@ -835,17 +850,27 @@ module Sequel
835
850
  # database with the table name given. Other arguments raise an +Error+.
836
851
  # Returns self.
837
852
  #
838
- # This changes the row_proc of the dataset to return
839
- # model objects and extends the dataset with the dataset_method_modules.
840
853
  # It also attempts to determine the database schema for the model,
841
854
  # based on the given dataset.
842
855
  #
843
- # Artist.set_dataset(:tbl_artists)
844
- # Artist.set_dataset(DB[:artists])
845
- #
846
856
  # Note that you should not use this to change the model's dataset
847
857
  # at runtime. If you have that need, you should look into Sequel's
848
858
  # sharding support.
859
+ #
860
+ # You should avoid calling this method directly. Instead of doing:
861
+ #
862
+ # class Artist < Sequel::Model
863
+ # set_dataset :tbl_artists
864
+ # end
865
+ #
866
+ # You should use:
867
+ #
868
+ # class Artist < Sequel::Model(:tbl_artists)
869
+ # end
870
+ #
871
+ # This ensures the class never uses an invalid dataset. Calling +set_dataset+
872
+ # after creating a class can create a class with initial invalid dataset, which
873
+ # will break when +require_valid_table+ or certain plugins are used.
849
874
  def set_dataset(ds, opts=OPTS)
850
875
  inherited = opts[:inherited]
851
876
  @dataset = convert_input_dataset(ds)
@@ -895,7 +920,6 @@ module Sequel
895
920
  # Cache of setter methods to allow by default, in order to speed up new/set/update instance methods.
896
921
  def setter_methods
897
922
  return @setter_methods if @setter_methods
898
- raise if frozen?
899
923
  @setter_methods = get_setter_methods
900
924
  end
901
925
 
@@ -937,7 +961,7 @@ module Sequel
937
961
  #
938
962
  # Artist.table_name # => :artists
939
963
  # Sequel::Model(:foo).table_name # => :foo
940
- # Sequel::Model(:foo___bar).table_name # => :bar
964
+ # Sequel::Model(Sequel[:foo].as(:bar)).table_name # => :bar
941
965
  def table_name
942
966
  dataset.first_source_alias
943
967
  end
@@ -1253,7 +1277,7 @@ module Sequel
1253
1277
  # should be used whenever the model's dataset is modified.
1254
1278
  def reset_instance_dataset
1255
1279
  Sequel.synchronize{@finders.clear if @finders}
1256
- @instance_dataset = @dataset.limit(1).naked if @dataset
1280
+ @instance_dataset = @dataset.limit(1).naked.skip_limit_check if @dataset
1257
1281
  end
1258
1282
 
1259
1283
  # Set the columns for this model and create accessor methods for each column.
@@ -1736,8 +1760,8 @@ module Sequel
1736
1760
  raise Sequel::Error, "can't save frozen object" if frozen?
1737
1761
  set_server(opts[:server]) if opts[:server]
1738
1762
  _before_validation
1739
- if opts[:validate] != false
1740
- unless checked_save_failure(opts){_valid?(true, opts)}
1763
+ if opts[:validate] != false # SEQUEL5: Remove if
1764
+ unless checked_save_failure(opts){_valid?(opts)}
1741
1765
  raise(ValidationFailed.new(self)) if raise_on_failure?(opts)
1742
1766
  return
1743
1767
  end
@@ -1931,12 +1955,16 @@ module Sequel
1931
1955
 
1932
1956
  # Validates the object and returns true if no errors are reported.
1933
1957
  #
1934
- # artist(:name=>'Valid').valid? # => true
1935
- # artist(:name=>'Invalid').valid? # => false
1958
+ # artist.set(:name=>'Valid').valid? # => true
1959
+ # artist.set(:name=>'Invalid').valid? # => false
1936
1960
  # artist.errors.full_messages # => ['name cannot be Invalid']
1937
1961
  def valid?(opts = OPTS)
1938
1962
  _before_validation
1939
- _valid?(false, opts)
1963
+ begin
1964
+ _valid?(opts)
1965
+ rescue HookFailed
1966
+ false
1967
+ end
1940
1968
  end
1941
1969
 
1942
1970
  private
@@ -1944,6 +1972,7 @@ module Sequel
1944
1972
  # Run code directly after the INSERT query, before after_create.
1945
1973
  # This is only a temporary API, it should not be overridden by external code.
1946
1974
  def _after_create(pk)
1975
+ # SEQUEL5: Remove
1947
1976
  @this = nil
1948
1977
  @new = false
1949
1978
  @was_new = true
@@ -1952,6 +1981,7 @@ module Sequel
1952
1981
  # Run code after around_save returns, before calling after_commit.
1953
1982
  # This is only a temporary API, it should not be overridden by external code.
1954
1983
  def _after_save(pk)
1984
+ # SEQUEL5: Remove
1955
1985
  if @was_new
1956
1986
  @was_new = nil
1957
1987
  pk ? _save_refresh : changed_columns.clear
@@ -1964,6 +1994,7 @@ module Sequel
1964
1994
  # Run code directly after the UPDATE query, before after_update.
1965
1995
  # This is only a temporary API, it should not be overridden by external code.
1966
1996
  def _after_update
1997
+ # SEQUEL5: Remove
1967
1998
  @this = nil
1968
1999
  end
1969
2000
 
@@ -2008,17 +2039,26 @@ module Sequel
2008
2039
  def _destroy(opts)
2009
2040
  sh = {:server=>this_server}
2010
2041
  uacr = use_after_commit_rollback
2011
- db.after_rollback(sh){after_destroy_rollback} if uacr.nil? ? (method(:after_destroy_rollback).owner != InstanceMethods) : uacr
2042
+ if uacr.nil? ? (method(:after_destroy_rollback).owner != InstanceMethods) : uacr
2043
+ Sequel::Deprecation.deprecate("Model#after_destroy_rollback", "Instead, call db.after_rollback in Model#before_destroy")
2044
+ db.after_rollback(sh){after_destroy_rollback}
2045
+ end
2012
2046
  called = false
2013
2047
  around_destroy do
2014
2048
  called = true
2015
- raise_hook_failure(:before_destroy) if before_destroy == false
2049
+ if before_destroy == false
2050
+ Sequel::Deprecation.deprecate("Having before_destroy return false to cancel the destroy", "Instead, call cancel_action inside before_destroy")
2051
+ raise_hook_failure(:before_destroy)
2052
+ end
2016
2053
  _destroy_delete
2017
2054
  after_destroy
2018
2055
  true
2019
2056
  end
2020
2057
  raise_hook_failure(:around_destroy) unless called
2021
- db.after_commit(sh){after_destroy_commit} if uacr.nil? ? (method(:after_destroy_commit).owner != InstanceMethods) : uacr
2058
+ if uacr.nil? ? (method(:after_destroy_commit).owner != InstanceMethods) : uacr
2059
+ Sequel::Deprecation.deprecate("Model#after_destroy_commit", "Instead, call db.after_commit in Model#after_destroy")
2060
+ db.after_commit(sh){after_destroy_commit}
2061
+ end
2022
2062
  self
2023
2063
  end
2024
2064
 
@@ -2095,19 +2135,34 @@ module Sequel
2095
2135
  def _save(opts)
2096
2136
  sh = {:server=>this_server}
2097
2137
  uacr = use_after_commit_rollback
2098
- db.after_rollback(sh){after_rollback} if uacr.nil? ? (method(:after_rollback).owner != InstanceMethods) : uacr
2138
+ if uacr.nil? ? (method(:after_rollback).owner != InstanceMethods) : uacr
2139
+ Sequel::Deprecation.deprecate("Model#after_rollback", "Instead, call db.after_rollback in Model#before_save.")
2140
+ db.after_rollback(sh){after_rollback}
2141
+ end
2099
2142
  pk = nil
2100
2143
  called_save = false
2101
2144
  called_cu = false
2102
2145
  around_save do
2103
2146
  called_save = true
2104
- raise_hook_failure(:before_save) if before_save == false
2147
+ if before_save == false
2148
+ Sequel::Deprecation.deprecate("Having before_save return false to cancel the save", "Instead, call cancel_action inside before_save")
2149
+ raise_hook_failure(:before_save)
2150
+ end
2151
+
2105
2152
  if new?
2106
2153
  around_create do
2107
2154
  called_cu = true
2108
- raise_hook_failure(:before_create) if before_create == false
2155
+ if before_create == false
2156
+ Sequel::Deprecation.deprecate("Having before_create return false to cancel the create", "Instead, call cancel_action inside before_create")
2157
+ raise_hook_failure(:before_create)
2158
+ end
2109
2159
  pk = _insert
2110
- _after_create(pk)
2160
+ _after_create(pk) # SEQUEL5: Remove
2161
+ # SEQUEL5
2162
+ # @this = nil
2163
+ # @new = false
2164
+ # @modified = false
2165
+ # pk ? _save_refresh : changed_columns.clear
2111
2166
  after_create
2112
2167
  true
2113
2168
  end
@@ -2115,10 +2170,13 @@ module Sequel
2115
2170
  else
2116
2171
  around_update do
2117
2172
  called_cu = true
2118
- raise_hook_failure(:before_update) if before_update == false
2173
+ if before_update == false
2174
+ Sequel::Deprecation.deprecate("Having before_update return false to cancel the update", "Instead, call cancel_action inside before_update")
2175
+ raise_hook_failure(:before_update)
2176
+ end
2119
2177
  columns = opts[:columns]
2120
2178
  if columns.nil?
2121
- @columns_updated = if opts[:changed]
2179
+ columns_updated = if opts[:changed] # SEQUEL5: Use local variable instead of instance variable
2122
2180
  @values.reject{|k,v| !changed_columns.include?(k)}
2123
2181
  else
2124
2182
  _save_update_all_columns_hash
@@ -2126,11 +2184,14 @@ module Sequel
2126
2184
  changed_columns.clear
2127
2185
  else # update only the specified columns
2128
2186
  columns = Array(columns)
2129
- @columns_updated = @values.reject{|k, v| !columns.include?(k)}
2187
+ columns_updated = @values.reject{|k, v| !columns.include?(k)}
2130
2188
  changed_columns.reject!{|c| columns.include?(c)}
2131
2189
  end
2132
- _update_columns(@columns_updated)
2133
- _after_update
2190
+ _update_columns(columns_updated)
2191
+ _after_update # SEQUEL5: Remove
2192
+ # SEQUEL5
2193
+ # @this = nil
2194
+ # @modified = false
2134
2195
  after_update
2135
2196
  true
2136
2197
  end
@@ -2140,11 +2201,14 @@ module Sequel
2140
2201
  true
2141
2202
  end
2142
2203
  raise_hook_failure(:around_save) unless called_save
2143
- _after_save(pk)
2144
- db.after_commit(sh){after_commit} if uacr.nil? ? (method(:after_commit).owner != InstanceMethods) : uacr
2204
+ _after_save(pk) # SEQUEL5: Remove
2205
+ if uacr.nil? ? (method(:after_commit).owner != InstanceMethods) : uacr
2206
+ Sequel::Deprecation.deprecate("Model#after_commit", "Instead, call db.after_commit in Model#after_save.")
2207
+ db.after_commit(sh){after_commit}
2208
+ end
2145
2209
  self
2146
2210
  end
2147
-
2211
+
2148
2212
  # Refresh the object after saving it, used to get
2149
2213
  # default values of all columns. Separated from _save so it
2150
2214
  # can be overridden to avoid the refresh.
@@ -2175,6 +2239,7 @@ module Sequel
2175
2239
  # Plugins can override this method in order to update with
2176
2240
  # additional columns, even when the column hash is initially empty.
2177
2241
  def _update_columns(columns)
2242
+ @columns_updated ||= DeprecatedColumnsUpdated.new(columns) # SEQUEL5: Remove
2178
2243
  _update(columns) unless columns.empty?
2179
2244
  end
2180
2245
 
@@ -2202,38 +2267,27 @@ module Sequel
2202
2267
  (!ds.opts[:select] || ds.opts[:returning]) && ds.supports_insert_select?
2203
2268
  end
2204
2269
 
2205
- # Internal validation method. If +raise_errors+ is +true+, hook
2206
- # failures will be raised as HookFailure exceptions. If it is
2207
- # +false+, +false+ will be returned instead.
2208
- def _valid?(raise_errors, opts)
2270
+ # Internal validation method, running validation hooks.
2271
+ def _valid?(opts)
2209
2272
  return errors.empty? if frozen?
2210
2273
  errors.clear
2211
2274
  called = false
2212
- error = false
2275
+ # skip_validate = opts[:validate] == false # SEQUEL5
2213
2276
  around_validation do
2214
2277
  called = true
2215
2278
  if before_validation == false
2216
- if raise_errors
2217
- raise_hook_failure(:before_validation)
2218
- else
2219
- error = true
2220
- end
2221
- false
2279
+ Sequel::Deprecation.deprecate("Having before_validation return false to mark the object as invalid", "Instead, call cancel_action inside before_validation")
2280
+ raise_hook_failure(:before_validation)
2222
2281
  else
2223
- validate
2282
+ validate # unless skip_validate # SEQUEL5
2224
2283
  after_validation
2225
- errors.empty?
2226
2284
  end
2227
2285
  end
2228
- error = true unless called
2229
- if error
2230
- if raise_errors
2231
- raise_hook_failure(:around_validation)
2232
- else
2233
- false
2234
- end
2235
- else
2286
+ # return true if skip_validate # SEQUEL5
2287
+ if called
2236
2288
  errors.empty?
2289
+ else
2290
+ raise_hook_failure(:around_validation)
2237
2291
  end
2238
2292
  end
2239
2293
 
@@ -2433,8 +2487,7 @@ module Sequel
2433
2487
  end
2434
2488
  end
2435
2489
 
2436
- # Dataset methods are methods that the model class extends its dataset with in
2437
- # the call to set_dataset.
2490
+ # DatasetMethods contains methods that all model datasets have.
2438
2491
  module DatasetMethods
2439
2492
  Dataset.def_deprecated_opts_setter(self, :model)
2440
2493
 
@@ -2618,7 +2671,7 @@ module Sequel
2618
2671
  # Artist.dataset.with_pk([1, 2])
2619
2672
  # # SELECT * FROM artists WHERE ((artists.id1 = 1) AND (artists.id2 = 2)) LIMIT 1
2620
2673
  def with_pk(pk)
2621
- if loader = _with_pk_loader
2674
+ if pk && (loader = _with_pk_loader)
2622
2675
  loader.first(*pk)
2623
2676
  else
2624
2677
  first(model.qualified_primary_key_hash(pk))
@@ -39,13 +39,14 @@ module Sequel
39
39
  end
40
40
 
41
41
  meths = (<<-METHS).split.map(&:to_sym)
42
- distinct eager grep group group_and_count group_append
42
+ distinct grep group group_and_count group_append
43
43
  limit offset order order_append order_prepend
44
44
  select select_all select_append select_group server
45
45
  METHS
46
46
 
47
- meths.each do |meth|
48
- define_method(meth) do |name, *args, &block|
47
+ # Define a method in the module
48
+ def self.def_dataset_caching_method(mod, meth)
49
+ mod.send(:define_method, meth) do |name, *args, &block|
49
50
  if block
50
51
  @model.def_dataset_method(name){send(meth, *args, &block)}
51
52
  else
@@ -57,6 +58,10 @@ module Sequel
57
58
  end
58
59
  end
59
60
 
61
+ meths.each do |meth|
62
+ def_dataset_caching_method(self, meth)
63
+ end
64
+
60
65
  private
61
66
 
62
67
  # Add a class method to the related model that
@@ -65,5 +70,7 @@ module Sequel
65
70
  @model.send(:def_model_dataset_method, meth)
66
71
  end
67
72
  end
73
+
74
+ @dataset_module_class = DatasetModule
68
75
  end
69
76
  end
@@ -15,17 +15,24 @@ module Sequel
15
15
 
16
16
  # Alias for HookFailed, kept for backwards compatibility
17
17
  BeforeHookFailed = HookFailed
18
+ Sequel::Deprecation.deprecate_constant(self, :BeforeHookFailed)
18
19
 
20
+ (
19
21
  # Exception class raised when +require_modification+ is set and an UPDATE or DELETE statement to modify the dataset doesn't
20
22
  # modify a single row.
21
23
  NoExistingObject = Class.new(Error)
24
+ ).name
22
25
 
26
+ (
23
27
  # Raised when an undefined association is used when eager loading.
24
28
  UndefinedAssociation = Class.new(Error)
29
+ ).name
25
30
 
31
+ (
26
32
  # Raised when a mass assignment method is called in strict mode with either a restricted column
27
33
  # or a column without a setter method.
28
34
  MassAssignmentRestriction = Class.new(Error)
35
+ ).name
29
36
 
30
37
  # Exception class raised when +raise_on_save_failure+ is set and validation fails
31
38
  class ValidationFailed < Error
@@ -49,9 +56,4 @@ module Sequel
49
56
  end
50
57
  end
51
58
  end
52
-
53
- # Call name on each class to set the name for the class, so it gets cached.
54
- constants.map{|c| const_get(c)}.each do |c|
55
- Class === c && c.name
56
- end
57
59
  end