sequel 3.21.0 → 3.36.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.
- data/CHANGELOG +855 -3
- data/MIT-LICENSE +1 -1
- data/README.rdoc +23 -7
- data/Rakefile +42 -24
- data/bin/sequel +26 -8
- data/doc/active_record.rdoc +1 -0
- data/doc/advanced_associations.rdoc +171 -11
- data/doc/association_basics.rdoc +293 -43
- data/doc/dataset_basics.rdoc +5 -5
- data/doc/dataset_filtering.rdoc +8 -0
- data/doc/mass_assignment.rdoc +56 -0
- data/doc/migration.rdoc +85 -552
- data/doc/model_hooks.rdoc +78 -27
- data/doc/object_model.rdoc +541 -0
- data/doc/opening_databases.rdoc +97 -50
- data/doc/prepared_statements.rdoc +40 -14
- data/doc/querying.rdoc +28 -4
- data/doc/reflection.rdoc +30 -4
- data/doc/release_notes/3.22.0.txt +39 -0
- data/doc/release_notes/3.23.0.txt +172 -0
- data/doc/release_notes/3.24.0.txt +420 -0
- data/doc/release_notes/3.25.0.txt +88 -0
- data/doc/release_notes/3.26.0.txt +88 -0
- data/doc/release_notes/3.27.0.txt +82 -0
- data/doc/release_notes/3.28.0.txt +304 -0
- data/doc/release_notes/3.29.0.txt +459 -0
- data/doc/release_notes/3.30.0.txt +135 -0
- data/doc/release_notes/3.31.0.txt +146 -0
- data/doc/release_notes/3.32.0.txt +202 -0
- data/doc/release_notes/3.33.0.txt +157 -0
- data/doc/release_notes/3.34.0.txt +671 -0
- data/doc/release_notes/3.35.0.txt +144 -0
- data/doc/release_notes/3.36.0.txt +245 -0
- data/doc/schema_modification.rdoc +572 -0
- data/doc/sharding.rdoc +95 -3
- data/doc/testing.rdoc +129 -0
- data/doc/thread_safety.rdoc +17 -0
- data/doc/transactions.rdoc +137 -0
- data/doc/virtual_rows.rdoc +51 -2
- data/lib/sequel/adapters/ado/mssql.rb +18 -6
- data/lib/sequel/adapters/ado.rb +40 -18
- data/lib/sequel/adapters/amalgalite.rb +17 -9
- data/lib/sequel/adapters/db2.rb +175 -86
- data/lib/sequel/adapters/dbi.rb +15 -15
- data/lib/sequel/adapters/do/mysql.rb +17 -11
- data/lib/sequel/adapters/do/postgres.rb +1 -57
- data/lib/sequel/adapters/do/sqlite.rb +0 -10
- data/lib/sequel/adapters/do.rb +18 -36
- data/lib/sequel/adapters/firebird.rb +27 -208
- data/lib/sequel/adapters/ibmdb.rb +453 -0
- data/lib/sequel/adapters/informix.rb +6 -23
- data/lib/sequel/adapters/jdbc/as400.rb +16 -34
- data/lib/sequel/adapters/jdbc/db2.rb +47 -0
- data/lib/sequel/adapters/jdbc/derby.rb +287 -0
- data/lib/sequel/adapters/jdbc/firebird.rb +24 -0
- data/lib/sequel/adapters/jdbc/h2.rb +73 -31
- data/lib/sequel/adapters/jdbc/hsqldb.rb +184 -0
- data/lib/sequel/adapters/jdbc/informix.rb +21 -0
- data/lib/sequel/adapters/jdbc/jtds.rb +29 -0
- data/lib/sequel/adapters/jdbc/mssql.rb +3 -33
- data/lib/sequel/adapters/jdbc/mysql.rb +7 -24
- data/lib/sequel/adapters/jdbc/oracle.rb +88 -25
- data/lib/sequel/adapters/jdbc/postgresql.rb +58 -48
- data/lib/sequel/adapters/jdbc/progress.rb +21 -0
- data/lib/sequel/adapters/jdbc/sqlite.rb +20 -10
- data/lib/sequel/adapters/jdbc/sqlserver.rb +66 -0
- data/lib/sequel/adapters/jdbc/transactions.rb +83 -0
- data/lib/sequel/adapters/jdbc.rb +265 -94
- data/lib/sequel/adapters/mock.rb +361 -0
- data/lib/sequel/adapters/mysql.rb +118 -222
- data/lib/sequel/adapters/mysql2.rb +58 -57
- data/lib/sequel/adapters/odbc/mssql.rb +15 -7
- data/lib/sequel/adapters/odbc.rb +28 -9
- data/lib/sequel/adapters/openbase.rb +3 -5
- data/lib/sequel/adapters/oracle.rb +349 -53
- data/lib/sequel/adapters/postgres.rb +356 -107
- data/lib/sequel/adapters/shared/access.rb +32 -9
- data/lib/sequel/adapters/shared/db2.rb +342 -0
- data/lib/sequel/adapters/shared/firebird.rb +221 -0
- data/lib/sequel/adapters/shared/informix.rb +53 -0
- data/lib/sequel/adapters/shared/mssql.rb +335 -118
- data/lib/sequel/adapters/shared/mysql.rb +340 -76
- data/lib/sequel/adapters/shared/mysql_prepared_statements.rb +155 -0
- data/lib/sequel/adapters/shared/oracle.rb +243 -45
- data/lib/sequel/adapters/shared/postgres.rb +524 -279
- data/lib/sequel/adapters/shared/progress.rb +5 -8
- data/lib/sequel/adapters/shared/sqlite.rb +265 -89
- data/lib/sequel/adapters/sqlite.rb +101 -39
- data/lib/sequel/adapters/swift/mysql.rb +9 -12
- data/lib/sequel/adapters/swift/postgres.rb +9 -74
- data/lib/sequel/adapters/swift/sqlite.rb +8 -6
- data/lib/sequel/adapters/swift.rb +8 -7
- data/lib/sequel/adapters/tinytds.rb +161 -21
- data/lib/sequel/adapters/utils/emulate_offset_with_row_number.rb +66 -0
- data/lib/sequel/adapters/utils/stored_procedures.rb +1 -11
- data/lib/sequel/ast_transformer.rb +194 -0
- data/lib/sequel/connection_pool/sharded_single.rb +11 -1
- data/lib/sequel/connection_pool/sharded_threaded.rb +28 -2
- data/lib/sequel/connection_pool/single.rb +5 -0
- data/lib/sequel/connection_pool/threaded.rb +38 -14
- data/lib/sequel/connection_pool.rb +10 -2
- data/lib/sequel/core.rb +118 -11
- data/lib/sequel/database/connecting.rb +38 -28
- data/lib/sequel/database/dataset.rb +4 -4
- data/lib/sequel/database/dataset_defaults.rb +63 -2
- data/lib/sequel/database/logging.rb +7 -2
- data/lib/sequel/database/misc.rb +150 -46
- data/lib/sequel/database/query.rb +215 -65
- data/lib/sequel/database/schema_generator.rb +64 -20
- data/lib/sequel/database/schema_methods.rb +212 -54
- data/lib/sequel/dataset/actions.rb +322 -85
- data/lib/sequel/dataset/features.rb +96 -8
- data/lib/sequel/dataset/graph.rb +38 -11
- data/lib/sequel/dataset/misc.rb +50 -23
- data/lib/sequel/dataset/mutation.rb +12 -7
- data/lib/sequel/dataset/prepared_statements.rb +68 -30
- data/lib/sequel/dataset/query.rb +237 -44
- data/lib/sequel/dataset/sql.rb +698 -278
- data/lib/sequel/dataset.rb +8 -0
- data/lib/sequel/exceptions.rb +4 -0
- data/lib/sequel/extensions/_pretty_table.rb +79 -0
- data/lib/sequel/extensions/arbitrary_servers.rb +108 -0
- data/lib/sequel/extensions/columns_introspection.rb +61 -0
- data/lib/sequel/{core_sql.rb → extensions/core_extensions.rb} +16 -34
- data/lib/sequel/extensions/migration.rb +97 -11
- data/lib/sequel/extensions/named_timezones.rb +5 -0
- data/lib/sequel/extensions/null_dataset.rb +90 -0
- data/lib/sequel/extensions/pg_array.rb +460 -0
- data/lib/sequel/extensions/pg_array_ops.rb +220 -0
- data/lib/sequel/extensions/pg_auto_parameterize.rb +169 -0
- data/lib/sequel/extensions/pg_hstore.rb +296 -0
- data/lib/sequel/extensions/pg_hstore_ops.rb +259 -0
- data/lib/sequel/extensions/pg_inet.rb +89 -0
- data/lib/sequel/extensions/pg_json.rb +178 -0
- data/lib/sequel/extensions/pg_statement_cache.rb +316 -0
- data/lib/sequel/extensions/pretty_table.rb +5 -71
- data/lib/sequel/extensions/query.rb +1 -1
- data/lib/sequel/extensions/query_literals.rb +79 -0
- data/lib/sequel/extensions/schema_caching.rb +76 -0
- data/lib/sequel/extensions/schema_dumper.rb +251 -37
- data/lib/sequel/extensions/select_remove.rb +35 -0
- data/lib/sequel/extensions/server_block.rb +139 -0
- data/lib/sequel/extensions/sql_expr.rb +4 -110
- data/lib/sequel/extensions/thread_local_timezones.rb +1 -1
- data/lib/sequel/extensions/to_dot.rb +95 -83
- data/lib/sequel/model/associations.rb +1187 -393
- data/lib/sequel/model/base.rb +578 -170
- data/lib/sequel/model/errors.rb +1 -1
- data/lib/sequel/model/exceptions.rb +5 -1
- data/lib/sequel/model/inflections.rb +1 -1
- data/lib/sequel/model.rb +30 -11
- data/lib/sequel/no_core_ext.rb +2 -0
- data/lib/sequel/plugins/active_model.rb +13 -1
- data/lib/sequel/plugins/association_pks.rb +22 -4
- data/lib/sequel/plugins/caching.rb +25 -18
- data/lib/sequel/plugins/class_table_inheritance.rb +4 -4
- data/lib/sequel/plugins/composition.rb +44 -12
- data/lib/sequel/plugins/dataset_associations.rb +100 -0
- data/lib/sequel/plugins/defaults_setter.rb +58 -0
- data/lib/sequel/plugins/dirty.rb +214 -0
- data/lib/sequel/plugins/eager_each.rb +59 -0
- data/lib/sequel/plugins/force_encoding.rb +6 -6
- data/lib/sequel/plugins/hook_class_methods.rb +1 -1
- data/lib/sequel/plugins/identity_map.rb +123 -8
- data/lib/sequel/plugins/instance_filters.rb +10 -0
- data/lib/sequel/plugins/instance_hooks.rb +1 -1
- data/lib/sequel/plugins/json_serializer.rb +58 -6
- data/lib/sequel/plugins/list.rb +12 -2
- data/lib/sequel/plugins/many_through_many.rb +79 -28
- data/lib/sequel/plugins/many_to_one_pk_lookup.rb +71 -0
- data/lib/sequel/plugins/nested_attributes.rb +139 -63
- data/lib/sequel/plugins/optimistic_locking.rb +8 -0
- data/lib/sequel/plugins/prepared_statements.rb +167 -0
- data/lib/sequel/plugins/prepared_statements_associations.rb +87 -0
- data/lib/sequel/plugins/prepared_statements_safe.rb +82 -0
- data/lib/sequel/plugins/prepared_statements_with_pk.rb +59 -0
- data/lib/sequel/plugins/rcte_tree.rb +29 -15
- data/lib/sequel/plugins/schema.rb +7 -2
- data/lib/sequel/plugins/serialization.rb +98 -49
- data/lib/sequel/plugins/serialization_modification_detection.rb +63 -0
- data/lib/sequel/plugins/sharding.rb +21 -54
- data/lib/sequel/plugins/single_table_inheritance.rb +5 -3
- data/lib/sequel/plugins/static_cache.rb +99 -0
- data/lib/sequel/plugins/subclasses.rb +10 -2
- data/lib/sequel/plugins/tactical_eager_loading.rb +7 -7
- data/lib/sequel/plugins/timestamps.rb +1 -1
- data/lib/sequel/plugins/typecast_on_load.rb +9 -12
- data/lib/sequel/plugins/update_primary_key.rb +2 -2
- data/lib/sequel/plugins/validation_class_methods.rb +1 -1
- data/lib/sequel/plugins/xml_serializer.rb +15 -4
- data/lib/sequel/sql.rb +526 -59
- data/lib/sequel/timezones.rb +57 -38
- data/lib/sequel/version.rb +1 -1
- data/spec/adapters/db2_spec.rb +146 -0
- data/spec/adapters/firebird_spec.rb +1 -1
- data/spec/adapters/mssql_spec.rb +142 -40
- data/spec/adapters/mysql_spec.rb +380 -234
- data/spec/adapters/oracle_spec.rb +67 -77
- data/spec/adapters/postgres_spec.rb +1050 -212
- data/spec/adapters/spec_helper.rb +8 -5
- data/spec/adapters/sqlite_spec.rb +139 -27
- data/spec/core/connection_pool_spec.rb +196 -93
- data/spec/core/database_spec.rb +879 -510
- data/spec/core/dataset_spec.rb +1415 -1086
- data/spec/core/expression_filters_spec.rb +554 -109
- data/spec/core/mock_adapter_spec.rb +449 -0
- data/spec/core/object_graph_spec.rb +86 -114
- data/spec/core/schema_generator_spec.rb +4 -4
- data/spec/core/schema_spec.rb +482 -38
- data/spec/core/spec_helper.rb +6 -48
- data/spec/extensions/active_model_spec.rb +13 -0
- data/spec/extensions/arbitrary_servers_spec.rb +110 -0
- data/spec/extensions/association_autoreloading_spec.rb +18 -10
- data/spec/extensions/association_dependencies_spec.rb +15 -25
- data/spec/extensions/association_pks_spec.rb +66 -32
- data/spec/extensions/association_proxies_spec.rb +4 -4
- data/spec/extensions/caching_spec.rb +47 -51
- data/spec/extensions/class_table_inheritance_spec.rb +31 -83
- data/spec/extensions/columns_introspection_spec.rb +91 -0
- data/spec/extensions/composition_spec.rb +18 -13
- data/spec/{core/core_sql_spec.rb → extensions/core_extensions_spec.rb} +119 -139
- data/spec/extensions/dataset_associations_spec.rb +199 -0
- data/spec/extensions/defaults_setter_spec.rb +64 -0
- data/spec/extensions/dirty_spec.rb +155 -0
- data/spec/extensions/eager_each_spec.rb +34 -0
- data/spec/extensions/force_encoding_spec.rb +4 -2
- data/spec/extensions/hook_class_methods_spec.rb +69 -92
- data/spec/extensions/identity_map_spec.rb +131 -22
- data/spec/extensions/inflector_spec.rb +0 -4
- data/spec/extensions/instance_filters_spec.rb +11 -21
- data/spec/extensions/instance_hooks_spec.rb +72 -0
- data/spec/extensions/json_serializer_spec.rb +49 -6
- data/spec/extensions/lazy_attributes_spec.rb +16 -20
- data/spec/extensions/list_spec.rb +48 -39
- data/spec/extensions/many_through_many_spec.rb +283 -250
- data/spec/extensions/many_to_one_pk_lookup_spec.rb +140 -0
- data/spec/extensions/migration_spec.rb +140 -35
- data/spec/extensions/named_timezones_spec.rb +29 -11
- data/spec/extensions/nested_attributes_spec.rb +251 -89
- data/spec/extensions/null_dataset_spec.rb +85 -0
- data/spec/extensions/optimistic_locking_spec.rb +24 -21
- data/spec/extensions/pg_array_ops_spec.rb +105 -0
- data/spec/extensions/pg_array_spec.rb +196 -0
- data/spec/extensions/pg_auto_parameterize_spec.rb +65 -0
- data/spec/extensions/pg_hstore_ops_spec.rb +136 -0
- data/spec/extensions/pg_hstore_spec.rb +195 -0
- data/spec/extensions/pg_inet_spec.rb +44 -0
- data/spec/extensions/pg_json_spec.rb +101 -0
- data/spec/extensions/pg_statement_cache_spec.rb +209 -0
- data/spec/extensions/prepared_statements_associations_spec.rb +111 -0
- data/spec/extensions/prepared_statements_safe_spec.rb +61 -0
- data/spec/extensions/prepared_statements_spec.rb +87 -0
- data/spec/extensions/prepared_statements_with_pk_spec.rb +31 -0
- data/spec/extensions/pretty_table_spec.rb +7 -6
- data/spec/extensions/query_literals_spec.rb +168 -0
- data/spec/extensions/query_spec.rb +6 -0
- data/spec/extensions/rcte_tree_spec.rb +50 -43
- data/spec/extensions/schema_caching_spec.rb +41 -0
- data/spec/extensions/schema_dumper_spec.rb +429 -22
- data/spec/extensions/schema_spec.rb +25 -21
- data/spec/extensions/select_remove_spec.rb +38 -0
- data/spec/extensions/serialization_modification_detection_spec.rb +72 -0
- data/spec/extensions/serialization_spec.rb +85 -43
- data/spec/extensions/server_block_spec.rb +90 -0
- data/spec/extensions/sharding_spec.rb +69 -143
- data/spec/extensions/single_table_inheritance_spec.rb +23 -29
- data/spec/extensions/skip_create_refresh_spec.rb +1 -1
- data/spec/extensions/spec_helper.rb +22 -61
- data/spec/extensions/sql_expr_spec.rb +29 -60
- data/spec/extensions/static_cache_spec.rb +145 -0
- data/spec/extensions/tactical_eager_loading_spec.rb +17 -19
- data/spec/extensions/thread_local_timezones_spec.rb +22 -2
- data/spec/extensions/timestamps_spec.rb +6 -6
- data/spec/extensions/to_dot_spec.rb +4 -7
- data/spec/extensions/touch_spec.rb +13 -14
- data/spec/extensions/tree_spec.rb +11 -26
- data/spec/extensions/typecast_on_load_spec.rb +9 -6
- data/spec/extensions/update_primary_key_spec.rb +30 -24
- data/spec/extensions/validation_class_methods_spec.rb +30 -51
- data/spec/extensions/validation_helpers_spec.rb +16 -35
- data/spec/extensions/xml_serializer_spec.rb +29 -4
- data/spec/files/transaction_specified_migrations/001_create_alt_basic.rb +4 -0
- data/spec/files/transaction_specified_migrations/002_create_basic.rb +4 -0
- data/spec/files/transaction_unspecified_migrations/001_create_alt_basic.rb +3 -0
- data/spec/files/transaction_unspecified_migrations/002_create_basic.rb +3 -0
- data/spec/integration/associations_test.rb +659 -21
- data/spec/integration/database_test.rb +9 -3
- data/spec/integration/dataset_test.rb +605 -91
- data/spec/integration/eager_loader_test.rb +19 -21
- data/spec/integration/migrator_test.rb +2 -3
- data/spec/integration/model_test.rb +81 -2
- data/spec/integration/plugin_test.rb +454 -143
- data/spec/integration/prepared_statement_test.rb +263 -128
- data/spec/integration/schema_test.rb +309 -43
- data/spec/integration/spec_helper.rb +40 -30
- data/spec/integration/timezone_test.rb +38 -12
- data/spec/integration/transaction_test.rb +183 -8
- data/spec/integration/type_test.rb +18 -4
- data/spec/model/association_reflection_spec.rb +201 -7
- data/spec/model/associations_spec.rb +1067 -661
- data/spec/model/base_spec.rb +329 -95
- data/spec/model/dataset_methods_spec.rb +7 -27
- data/spec/model/eager_loading_spec.rb +677 -676
- data/spec/model/hooks_spec.rb +349 -67
- data/spec/model/model_spec.rb +240 -168
- data/spec/model/plugins_spec.rb +24 -13
- data/spec/model/record_spec.rb +490 -232
- data/spec/model/spec_helper.rb +14 -71
- data/spec/model/validations_spec.rb +11 -0
- data/spec/rcov.opts +2 -0
- metadata +178 -80
data/doc/association_basics.rdoc
CHANGED
|
@@ -247,7 +247,7 @@ example is a tree structure:
|
|
|
247
247
|
|
|
248
248
|
class Node
|
|
249
249
|
many_to_one :parent, :class=>self
|
|
250
|
-
one_to_many :children :key=>:parent_id, :class=>self
|
|
250
|
+
one_to_many :children, :key=>:parent_id, :class=>self
|
|
251
251
|
end
|
|
252
252
|
|
|
253
253
|
For many_to_many self_referential associations, it's fairly similar. Here's
|
|
@@ -293,32 +293,6 @@ Examples:
|
|
|
293
293
|
@artist.remove_album(@album)
|
|
294
294
|
@artist.remove_all_albums
|
|
295
295
|
|
|
296
|
-
== Dataset Method
|
|
297
|
-
|
|
298
|
-
In addition to the above methods, associations also add a instance method
|
|
299
|
-
ending in +_dataset+ that returns a dataset representing the objects in the associated table:
|
|
300
|
-
|
|
301
|
-
@album.artist_id
|
|
302
|
-
# 10
|
|
303
|
-
@album.artist_dataset
|
|
304
|
-
# SELECT * FROM artists WHERE (id = 10)
|
|
305
|
-
|
|
306
|
-
@artist.id
|
|
307
|
-
# 20
|
|
308
|
-
@artist.albums_dataset
|
|
309
|
-
# SELECT * FROM albums WHERE (artist_id = 20)
|
|
310
|
-
|
|
311
|
-
The association dataset is just like any other Sequel dataset, in that
|
|
312
|
-
it can be further filtered, ordered, etc.:
|
|
313
|
-
|
|
314
|
-
@artist.albums_dataset.
|
|
315
|
-
filter(:name.like('A%')).
|
|
316
|
-
order(:copies_sold).
|
|
317
|
-
limit(10)
|
|
318
|
-
# SELECT * FROM albums
|
|
319
|
-
# WHERE ((artist_id = 20) AND (name LIKE 'A%'))
|
|
320
|
-
# ORDER BY copies_sold LIMIT 10
|
|
321
|
-
|
|
322
296
|
== Caching
|
|
323
297
|
|
|
324
298
|
Associations are cached after being retrieved:
|
|
@@ -352,13 +326,150 @@ instance method:
|
|
|
352
326
|
@album.artists # [<Artist ...>, ...]
|
|
353
327
|
@album.associations[:artists] # [<Artist ...>, ...]
|
|
354
328
|
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
329
|
+
== Dataset Method
|
|
330
|
+
|
|
331
|
+
In addition to the above methods, associations also add a instance method
|
|
332
|
+
ending in +_dataset+ that returns a dataset representing the objects in the associated table:
|
|
333
|
+
|
|
334
|
+
@album.artist_id
|
|
335
|
+
# 10
|
|
336
|
+
@album.artist_dataset
|
|
337
|
+
# SELECT * FROM artists WHERE (id = 10)
|
|
338
|
+
|
|
339
|
+
@artist.id
|
|
340
|
+
# 20
|
|
341
|
+
@artist.albums_dataset
|
|
342
|
+
# SELECT * FROM albums WHERE (artist_id = 20)
|
|
343
|
+
|
|
344
|
+
The association dataset is just like any other Sequel dataset, in that
|
|
345
|
+
it can be further filtered, ordered, etc.:
|
|
346
|
+
|
|
347
|
+
@artist.albums_dataset.
|
|
348
|
+
filter(:name.like('A%')).
|
|
349
|
+
order(:copies_sold).
|
|
350
|
+
limit(10)
|
|
351
|
+
# SELECT * FROM albums
|
|
352
|
+
# WHERE ((artist_id = 20) AND (name LIKE 'A%'))
|
|
353
|
+
# ORDER BY copies_sold LIMIT 10
|
|
354
|
+
|
|
355
|
+
Records retrieved using the +_dataset+ method are not cached in the
|
|
356
|
+
associations cache.
|
|
358
357
|
|
|
359
358
|
@album.artists_dataset.all # [<Artist ...>, ...]
|
|
360
359
|
@album.associations[:artists] # nil
|
|
361
360
|
|
|
361
|
+
== Dynamic Association Modification
|
|
362
|
+
|
|
363
|
+
Similar to the +_dataset+ method, you can provide a block to the association
|
|
364
|
+
method to customize the dataset that will be used to retrieve the records. So
|
|
365
|
+
you can apply a filter in either of these two ways:
|
|
366
|
+
|
|
367
|
+
@artist.albums_dataset.filter(:name.like('A%'))
|
|
368
|
+
@artist.albums{|ds| ds.filter(:name.like('A%'))}
|
|
369
|
+
|
|
370
|
+
While they both apply the same filter, using the +_dataset+ method does not
|
|
371
|
+
apply any of the association callbacks or handle association reciprocals (see
|
|
372
|
+
below for details about callbacks and reciprocals). Using a block instead handles
|
|
373
|
+
all those things, and also caches its results in the associations cache (ignoring
|
|
374
|
+
any previously cached value).
|
|
375
|
+
|
|
376
|
+
Note that if you are using ruby 1.8.6, you can't pass a block to the association
|
|
377
|
+
method, you have to pass a proc as an argument:
|
|
378
|
+
|
|
379
|
+
@artist.albums(proc{|ds| ds.filter(:name.like('A%'))})
|
|
380
|
+
|
|
381
|
+
== Filtering By Associations
|
|
382
|
+
|
|
383
|
+
In addition to using the association method to get associated objects, you
|
|
384
|
+
can also use associated objects in filters. For example, to get
|
|
385
|
+
all albums for a given artist, you would usually do:
|
|
386
|
+
|
|
387
|
+
@artist.albums
|
|
388
|
+
# or @artist.albums_dataset for a dataset
|
|
389
|
+
|
|
390
|
+
You can also do the following:
|
|
391
|
+
|
|
392
|
+
Album.filter(:artist=>@artist).all
|
|
393
|
+
# or leave off the .all for a dataset
|
|
394
|
+
|
|
395
|
+
For filtering by a single association, this isn't very useful. However, unlike
|
|
396
|
+
using the association method, using a filter allows you to filter by multiple
|
|
397
|
+
associations:
|
|
398
|
+
|
|
399
|
+
Album.filter(:artist=>@artist, :publisher=>@publisher)
|
|
400
|
+
|
|
401
|
+
This will return all albums by that artist and published by that publisher.
|
|
402
|
+
This isn't possible using just the association method approach, though you
|
|
403
|
+
can combine the approaches:
|
|
404
|
+
|
|
405
|
+
@artist.albums_dataset.filter(:publisher=>@publisher)
|
|
406
|
+
|
|
407
|
+
This doesn't just work for +many_to_one+ associations, it also works for
|
|
408
|
+
+one_to_one+, +one_to_many+, and +many_to_many+ associations:
|
|
409
|
+
|
|
410
|
+
Album.one_to_one :album_info
|
|
411
|
+
# The album related to that AlbumInfo instance
|
|
412
|
+
Album.filter(:album_info=>AlbumInfo[2])
|
|
413
|
+
|
|
414
|
+
Album.one_to_many :tracks
|
|
415
|
+
# The album related to that Track instance
|
|
416
|
+
Album.filter(:tracks=>Track[3])
|
|
417
|
+
|
|
418
|
+
Album.many_to_many :tags
|
|
419
|
+
# All albums related to that Tag instance
|
|
420
|
+
Album.filter(:tags=>Tag[4])
|
|
421
|
+
|
|
422
|
+
Note that for +one_to_many+ and +many_to_many+ associations, you still
|
|
423
|
+
use the plural form even though only a single model object is given.
|
|
424
|
+
|
|
425
|
+
You can also exclude by associations:
|
|
426
|
+
|
|
427
|
+
Album.exclude(:artist=>@artist).all
|
|
428
|
+
|
|
429
|
+
This will return all albums not by that artist.
|
|
430
|
+
|
|
431
|
+
You can also provide an array with multiple model objects:
|
|
432
|
+
|
|
433
|
+
Album.filter(:artist=>[@artist1, @artist2]).all
|
|
434
|
+
|
|
435
|
+
Similar to using an array of integers or strings, this will return
|
|
436
|
+
all albums whose artist is one of those two artists. You can also
|
|
437
|
+
use +exclude+ if you want all albums not by either of those artists:
|
|
438
|
+
|
|
439
|
+
Album.exclude(:artist=>[@artist1, @artist2]).all
|
|
440
|
+
|
|
441
|
+
If you are using a +one_to_many+ or +many_to_many+ association, you
|
|
442
|
+
may want to return records where the records matches all of multiple
|
|
443
|
+
records, instead of matching any of them. For example:
|
|
444
|
+
|
|
445
|
+
Album.filter(:tags=>[@tag1, @tag2])
|
|
446
|
+
|
|
447
|
+
This matches albums that are associated with either @tag1 or @tag2 or
|
|
448
|
+
both. If you only want ones that you are associated with both, you can
|
|
449
|
+
use separate filter calls:
|
|
450
|
+
|
|
451
|
+
Album.filter(:tags=>@tag1).filter(:tags=>@tag2)
|
|
452
|
+
|
|
453
|
+
Or the the array form of condition specifiers:
|
|
454
|
+
|
|
455
|
+
Album.filter([[:tags, @tag1], [:tags, @tag2]])
|
|
456
|
+
|
|
457
|
+
These will return albums associated with both @tag1 and @tag2.
|
|
458
|
+
|
|
459
|
+
You can also provide a dataset value when filtering by associations:
|
|
460
|
+
|
|
461
|
+
Album.filter(:artist=>Artist.filter(:name.like('A%'))).all
|
|
462
|
+
|
|
463
|
+
This will return all albums whose artist starts with 'A'. Like
|
|
464
|
+
the other forms, this can be inverted:
|
|
465
|
+
|
|
466
|
+
Album.exclude(:artist=>Artist.filter(:name.like('A%'))).all
|
|
467
|
+
|
|
468
|
+
This will return all albums whose artist does not start with 'A'.
|
|
469
|
+
|
|
470
|
+
Note that filtering by associations only works correctly for simple
|
|
471
|
+
associations (ones without conditions).
|
|
472
|
+
|
|
362
473
|
== Name Collisions
|
|
363
474
|
|
|
364
475
|
Because associations create instance methods, it's possible to override
|
|
@@ -368,7 +479,7 @@ would be bad association names.
|
|
|
368
479
|
|
|
369
480
|
== Database Schema
|
|
370
481
|
|
|
371
|
-
Creating an association
|
|
482
|
+
Creating an association doesn't modify the database schema. Sequel
|
|
372
483
|
assumes your associations reflect the existing database schema. If not,
|
|
373
484
|
you should modify your schema before creating the associations.
|
|
374
485
|
|
|
@@ -1055,7 +1166,7 @@ when eager loading via eager_graph, but called when eager loading via eager.
|
|
|
1055
1166
|
class Artist
|
|
1056
1167
|
# Cache all album names to a single string when retrieving the
|
|
1057
1168
|
# albums.
|
|
1058
|
-
one_to_many :albums, :
|
|
1169
|
+
one_to_many :albums, :after_load=>:cache_album_names
|
|
1059
1170
|
|
|
1060
1171
|
attr_reader :album_names
|
|
1061
1172
|
|
|
@@ -1218,25 +1329,44 @@ a JOIN USING or NATURAL JOIN for the graph:
|
|
|
1218
1329
|
Artist.one_to_many :albums, :key=>:artist_name,
|
|
1219
1330
|
:graph_only_conditions=>nil, :graph_join_type=>:natural
|
|
1220
1331
|
|
|
1332
|
+
==== :graph_alias_base
|
|
1333
|
+
|
|
1334
|
+
The base name to use for the table alias when eager graphing. Defaults to the name
|
|
1335
|
+
of the association. If the alias name has already been used in the query, Sequel will create
|
|
1336
|
+
a unique alias by appending a numeric suffix (e.g. alias_0, alias_1, ...) until the alias is
|
|
1337
|
+
unique.
|
|
1338
|
+
|
|
1339
|
+
This is mostly useful if you have associations with the same name in many models, and you want
|
|
1340
|
+
to be able to easily tell which table alias corresponds to which association when eagerly
|
|
1341
|
+
graphing multiple associations with the same name.
|
|
1342
|
+
|
|
1221
1343
|
==== :eager_grapher
|
|
1222
1344
|
|
|
1223
1345
|
Sets up a custom grapher to use when eager loading the objects via eager_graph.
|
|
1224
|
-
This is the eager_graph analogue to the :eager_loader option.
|
|
1346
|
+
This is the eager_graph analogue to the :eager_loader option. This isn't generally
|
|
1347
|
+
needed, as one of the other eager_graph related association options is usually sufficient.
|
|
1348
|
+
|
|
1349
|
+
If specified, should be a proc that accepts one or three three arguments.
|
|
1350
|
+
If the proc takes one argument, it will be given a hash with the following keys:
|
|
1225
1351
|
|
|
1226
|
-
|
|
1227
|
-
|
|
1228
|
-
was used for the current table (since you can cascade associations).
|
|
1229
|
-
|
|
1352
|
+
:self :: The dataset that is doing the eager loading
|
|
1353
|
+
:table_alias :: An alias to use for the table to graph for this association.
|
|
1354
|
+
:implicit_qualifier :: The alias that was used for the current table (since you can cascade associations).
|
|
1355
|
+
:callback :: A callback proc used to dynamically modify the dataset to graph into the
|
|
1356
|
+
current dataset, before such graphing is done. This is nil if no callback
|
|
1357
|
+
proc is used.
|
|
1358
|
+
|
|
1359
|
+
If the proc takes three arguments, it gets passed the :self, :association_alias,
|
|
1360
|
+
and :table_alias values. The 3 argument procs are allowed for backwards
|
|
1361
|
+
compatibility, and it is recommended to use the 1 argument proc format
|
|
1362
|
+
for new code.
|
|
1230
1363
|
|
|
1231
1364
|
Artist.one_to_many :self_title_albums, :class=>:Album,
|
|
1232
|
-
:eager_grapher=>(proc do |
|
|
1233
|
-
|
|
1234
|
-
:table_alias=>
|
|
1365
|
+
:eager_grapher=>(proc do |eo|
|
|
1366
|
+
eo[:self].graph(Album, {:artist_id=>:id, :name=>:name},
|
|
1367
|
+
:table_alias=>eo[:table_alias], :implicit_qualifier=>eo[:implicit_qualifier])
|
|
1235
1368
|
end)
|
|
1236
1369
|
|
|
1237
|
-
This isn't generally needed, as one of the other eager_graph related
|
|
1238
|
-
association options is usually sufficient.
|
|
1239
|
-
|
|
1240
1370
|
==== :order_eager_graph
|
|
1241
1371
|
|
|
1242
1372
|
Whether to add the order to the dataset's order when graphing via eager_graph.
|
|
@@ -1300,6 +1430,78 @@ by the foreign/primary keys. This option causes the
|
|
|
1300
1430
|
you want to replace the default foreign/primary key conditions that Sequel
|
|
1301
1431
|
would use when eagerly graphing.
|
|
1302
1432
|
|
|
1433
|
+
=== Column Naming Conflict Options
|
|
1434
|
+
|
|
1435
|
+
Sequel's association support historically called methods on model objects
|
|
1436
|
+
to get primary key or foreign key values instead of accessing the column
|
|
1437
|
+
values directly, in order to allow advanced features such as associations
|
|
1438
|
+
based on virtual column keys. Unfortunately, that causes issues if columns
|
|
1439
|
+
are used with names that clash with existing method names, which can happen
|
|
1440
|
+
if you want to name the association the same name as an existing column, or
|
|
1441
|
+
if the column has the same name as an already defined method such as
|
|
1442
|
+
<tt>object_id</tt>.
|
|
1443
|
+
|
|
1444
|
+
Sequel has added the following options that allow you to work around the
|
|
1445
|
+
issue by either specifying the column name symbol or the method name symbol
|
|
1446
|
+
to use. In most cases, these methods are designed to be used with column
|
|
1447
|
+
aliases defined with <tt>Model.def_column_alias</tt>:
|
|
1448
|
+
|
|
1449
|
+
# Example schema:
|
|
1450
|
+
# albums artists
|
|
1451
|
+
# :id /--> :id
|
|
1452
|
+
# :artist --/ :name
|
|
1453
|
+
# :name
|
|
1454
|
+
class Album < Sequel::Model
|
|
1455
|
+
def_column_alias(:artist_id, :artist)
|
|
1456
|
+
many_to_one :artist, :key=>:artist_id, :key_column=>:artist
|
|
1457
|
+
end
|
|
1458
|
+
|
|
1459
|
+
# Example schema:
|
|
1460
|
+
# things objs
|
|
1461
|
+
# :id /--> :id
|
|
1462
|
+
# :object_id --/ :name
|
|
1463
|
+
# :name
|
|
1464
|
+
class Thing < Sequel::Model
|
|
1465
|
+
def_column_alias(:obj_id, :object_id)
|
|
1466
|
+
end
|
|
1467
|
+
class Obj < Sequel::Model
|
|
1468
|
+
many_to_one :things, :key=>:object_id, :key_method=>:obj_id
|
|
1469
|
+
end
|
|
1470
|
+
|
|
1471
|
+
Note that for eager loading purposes, you generally need to set the
|
|
1472
|
+
<tt>:eager_loader_key</tt> option as well, specifying the underlying
|
|
1473
|
+
column(s) to use.
|
|
1474
|
+
|
|
1475
|
+
==== :key_column [+many_to_one+]
|
|
1476
|
+
|
|
1477
|
+
Like the :key option, but :key references the method name, while
|
|
1478
|
+
:key_column references the underlying column.
|
|
1479
|
+
|
|
1480
|
+
==== :primary_key_method [+many_to_one+]
|
|
1481
|
+
|
|
1482
|
+
Like the :primary_key option, but :primary_key references the column
|
|
1483
|
+
name, while :primary_key_method references the method name.
|
|
1484
|
+
|
|
1485
|
+
==== :primary_key_column [+one_to_many+, +one_to_one+]
|
|
1486
|
+
|
|
1487
|
+
Like the :primary_key option, but :primary_key references the method name, while
|
|
1488
|
+
:primary_key_column references the underlying column.
|
|
1489
|
+
|
|
1490
|
+
==== :key_method [+one_to_many+, +one_to_one+]
|
|
1491
|
+
|
|
1492
|
+
Like the :key option, but :key references the column
|
|
1493
|
+
name, while :key_method references the method name.
|
|
1494
|
+
|
|
1495
|
+
==== :left_primary_key_column [+many_to_many+]
|
|
1496
|
+
|
|
1497
|
+
Like the :left_primary_key option, but :left_primary_key references the method name, while
|
|
1498
|
+
:left_primary_key_column references the underlying column.
|
|
1499
|
+
|
|
1500
|
+
==== :right_primary_key_method [+many_to_many+]
|
|
1501
|
+
|
|
1502
|
+
Like the :right_primary_key option, but :right_primary_key references the column
|
|
1503
|
+
name, while :right_primary_key_method references the method name.
|
|
1504
|
+
|
|
1303
1505
|
=== Advanced Options
|
|
1304
1506
|
|
|
1305
1507
|
==== :reciprocal
|
|
@@ -1399,3 +1601,51 @@ associations depends on another plugin that defines instance methods of
|
|
|
1399
1601
|
the same name. In that case, the instance methods of the dependent
|
|
1400
1602
|
plugin would override the association methods created by the main
|
|
1401
1603
|
plugin.
|
|
1604
|
+
|
|
1605
|
+
==== :eager_limit_strategy
|
|
1606
|
+
|
|
1607
|
+
This setting determines what strategy to use for loading the associations
|
|
1608
|
+
that use the :limit setting to limit the number of returned records. You
|
|
1609
|
+
can't use LIMIT directly, since you want a limit for each associated
|
|
1610
|
+
record, not a LIMIT on the number of records returned by the dataset.
|
|
1611
|
+
|
|
1612
|
+
By default, no strategy is used for one_to_one associations, and
|
|
1613
|
+
the :ruby strategy is used for *_many associations, which does a simple
|
|
1614
|
+
array slice after loading the associated records. That doesn't provide
|
|
1615
|
+
a performance advantage, since all records are still loaded from the
|
|
1616
|
+
database, but it at least makes sure the cached records are accurately
|
|
1617
|
+
limited as they would be in the lazy load case.
|
|
1618
|
+
|
|
1619
|
+
The reason no strategy is used by default for one_to_one associations
|
|
1620
|
+
is that none is needed for a true one_to_one association (since there
|
|
1621
|
+
is only one associated record per current record). However, if you are
|
|
1622
|
+
using a one_to_one association where the relationship is really one_to_many,
|
|
1623
|
+
and using an order to pick the first matching row, then if you don't
|
|
1624
|
+
specify an :eager_limit_strategy option, you'll be loading all related
|
|
1625
|
+
rows just to have Sequel ignore all rows after the first. By using a
|
|
1626
|
+
strategy to change the query to only return one associated record per
|
|
1627
|
+
current record, you can get much better database performance.
|
|
1628
|
+
|
|
1629
|
+
You can set a value of +true+ for this option to have Sequel select what
|
|
1630
|
+
it thinks is the best way of limiting the records for your database. You
|
|
1631
|
+
can also specify a symbol to manually choose a strategy. The available
|
|
1632
|
+
strategies are:
|
|
1633
|
+
|
|
1634
|
+
:distinct_on :: Uses DISTINCT ON to ensure only the first matching record
|
|
1635
|
+
is loaded (one_to_one associations only). This is used by
|
|
1636
|
+
default on PostgreSQL.
|
|
1637
|
+
:window_function :: Uses window functions if the database supports it.
|
|
1638
|
+
This is used by default on databases that support window
|
|
1639
|
+
functions.
|
|
1640
|
+
:correlated_subquery :: Uses a correlated subquery to get the information.
|
|
1641
|
+
This is never used by default as if you aren't careful,
|
|
1642
|
+
it can result in pathologically long running times.
|
|
1643
|
+
This will not work correctly for associations where
|
|
1644
|
+
the associated table has a composite primary key if
|
|
1645
|
+
the database doesn't support using IN
|
|
1646
|
+
with multiple columns. This will also not work on MySQL
|
|
1647
|
+
because MySQL has problems using IN with a correlated
|
|
1648
|
+
subquery that contains a limit.
|
|
1649
|
+
:ruby :: Uses ruby array slicing to emulate database limiting (*_many
|
|
1650
|
+
associations only). This is the default if the database doesn't
|
|
1651
|
+
support window functions.
|
data/doc/dataset_basics.rdoc
CHANGED
|
@@ -74,12 +74,12 @@ Most Dataset methods that users will use can be broken down into two types:
|
|
|
74
74
|
|
|
75
75
|
Most dataset methods fall into this category, which can be further broken down by the clause they affect:
|
|
76
76
|
|
|
77
|
-
SELECT:: select, select_all, select_append, select_more
|
|
77
|
+
SELECT:: select, select_all, select_append, select_group, select_more
|
|
78
78
|
FROM:: from, from_self
|
|
79
79
|
JOIN:: join, left_join, right_join, full_join, natural_join, natural_left_join, natural_right_join, natural_full_join, cross_join, inner_join, left_outer_join, right_outer_join, full_outer_join, join_table
|
|
80
|
-
WHERE:: where, filter, exclude, and, or, grep, invert, unfiltered
|
|
81
|
-
GROUP:: group, group_by, group_and_count, ungrouped
|
|
82
|
-
HAVING:: having, filter, exclude, and, or, grep, invert, unfiltered
|
|
80
|
+
WHERE:: where, filter, exclude, exclude_where, and, or, grep, invert, unfiltered
|
|
81
|
+
GROUP:: group, group_by, group_and_count, select_group, ungrouped
|
|
82
|
+
HAVING:: having, filter, exclude, exclude_having, and, or, grep, invert, unfiltered
|
|
83
83
|
ORDER:: order, order_by, order_append, order_prepend, order_more, reverse, reverse_order, unordered
|
|
84
84
|
LIMIT:: limit, unlimited
|
|
85
85
|
compounds:: union, intersect, except
|
|
@@ -93,7 +93,7 @@ other:: clone, distinct, naked, server, with_sql
|
|
|
93
93
|
|
|
94
94
|
Most other dataset methods commonly used will execute the dataset's SQL on the database:
|
|
95
95
|
|
|
96
|
-
SELECT (All Records):: all, each, map, to_hash, select_map, select_order_map, select_hash, to_csv
|
|
96
|
+
SELECT (All Records):: all, each, map, to_hash, to_hash_groups, select_map, select_order_map, select_hash, select_hash_groups, to_csv
|
|
97
97
|
SELECT (First Record):: first, last, get, []
|
|
98
98
|
SELECT (Aggregates):: count, avg, max, min, sum, range, interval
|
|
99
99
|
INSERT:: insert, <<, import, multi_insert, insert_multiple
|
data/doc/dataset_filtering.rdoc
CHANGED
|
@@ -59,6 +59,14 @@ Ranges (both inclusive and exclusive) can also be used:
|
|
|
59
59
|
items.filter(:price => 100...200).sql
|
|
60
60
|
#=> "SELECT * FROM items WHERE (price >= 100 AND price < 200)"
|
|
61
61
|
|
|
62
|
+
== Filtering using an array
|
|
63
|
+
|
|
64
|
+
If you need to select multiple items from a dataset, you can supply an array:
|
|
65
|
+
|
|
66
|
+
item_array = [1, 38, 47, 99]
|
|
67
|
+
items.filter(:id => item_array).sql
|
|
68
|
+
#=> "SELECT * FROM items WHERE (id IN (1, 38, 47, 99))"
|
|
69
|
+
|
|
62
70
|
== Filtering using expressions
|
|
63
71
|
|
|
64
72
|
Sequel allows you to use ruby expressions directly in the call to filter:
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
= Sequel::Model Mass Assignment
|
|
2
|
+
|
|
3
|
+
Most Model methods that take a hash of attribute keys and values, including <tt>Model.new</tt>, <tt>Model.create</tt>, <tt>Model#set</tt> and <tt>Model#update</tt> are subject to Sequel's mass assignment rules.
|
|
4
|
+
When you pass a hash to these methods, each key has an <tt>=</tt> appended to it (the setter method), and if the setter method exists and access to it is not restricted, Sequel will call the setter method with the hash value.
|
|
5
|
+
By default, there are two types of setter methods that are restricted.
|
|
6
|
+
The first is methods like <tt>typecast_on_assignment=</tt> and <tt>==</tt>, which don't affect columns.
|
|
7
|
+
These methods cannot be enabled for mass assignment.
|
|
8
|
+
The second is primary key setters.
|
|
9
|
+
To enable use of primary key setters, you need to call +unrestrict_primary_key+ for that model:
|
|
10
|
+
|
|
11
|
+
Post.unrestrict_primary_key
|
|
12
|
+
|
|
13
|
+
Since mass assignment by default allows modification of all column values except for primary key columns, it can be a security risk in some cases.
|
|
14
|
+
Sequel has multiple ways of securing mass assignment.
|
|
15
|
+
The first way is using +set_allowed_columns+:
|
|
16
|
+
|
|
17
|
+
Post.set_allowed_columns :title, :body, :category
|
|
18
|
+
|
|
19
|
+
This explicitly sets which methods are allowed (<tt>title=</tt>, <tt>body=</tt>, and <tt>category=</tt>), all other methods will not be allowed.
|
|
20
|
+
This method is useful in simple applications where the same columns are allowed in all cases, but not appropriate when different columns are allowed in different scenarios (e.g. admin access vs. user access).
|
|
21
|
+
To handle cases where different columns are allowed in different cases, you can use +set_only+ or +update_only+:
|
|
22
|
+
|
|
23
|
+
# user case
|
|
24
|
+
post.set_only(params[:post], :title, :body)
|
|
25
|
+
# admin case
|
|
26
|
+
post.set_only(params[:post], :title, :body, :deleted)
|
|
27
|
+
|
|
28
|
+
In this case, only the <tt>title=</tt> and <tt>body=</tt> methods will be allowed in the mass assignment.
|
|
29
|
+
|
|
30
|
+
By default, if an invalid setter method call is attempted, Sequel raises a <tt>Sequel::Error</tt> exception. You can have Sequel silently ignore invalid calls by doing:
|
|
31
|
+
|
|
32
|
+
# Global default
|
|
33
|
+
Sequel::Model.strict_param_setting = false
|
|
34
|
+
# Class level
|
|
35
|
+
Post.strict_param_setting = false
|
|
36
|
+
# Instance level
|
|
37
|
+
post.strict_param_setting = false
|
|
38
|
+
|
|
39
|
+
These mass assignment methods have been around a long time, but starting in Sequel 3.12.0, the +set_fields+ and +update_fields+ methods were added, and these may be a better mass assignment choice for most users.
|
|
40
|
+
These methods take two arguments, the attributes hash as the first argument, and a single array of valid field names as the second argument:
|
|
41
|
+
|
|
42
|
+
post.set_fields(params[:post], [:title, :body])
|
|
43
|
+
|
|
44
|
+
+set_fields+ and +update_fields+ differ in implementation from +set_only+ and +update_only+.
|
|
45
|
+
With +set_only+ and +update_only+, the hash is iterated over and it checks each method call attempt to see if it is valid.
|
|
46
|
+
With +set_fields+ and +update_fields+, the array is iterated over, and it just looks up the value in the hash and calls the appropriate setter method.
|
|
47
|
+
|
|
48
|
+
+set_fields+ and +update_fields+ are designed for the case where you are expecting specific fields in the input, and want to ignore the other fields.
|
|
49
|
+
They work great for things like HTML forms where the form fields are static.
|
|
50
|
+
+set_only+ and +update_only+ are designed for cases where you are not sure what fields are going to be present in the input, but still want to make sure only certain setter methods can be called.
|
|
51
|
+
They work great for flexible APIs.
|
|
52
|
+
|
|
53
|
+
Starting in Sequel 3.34.0, +set_fields+ and +update_fields+ take an optional argument hash, and currently handles the :missing option. With <tt>:missing=>:skip</tt>, +set_fields+ and +update_fields+ will just skip missing entries in the hash, allowing them to be used in flexible APIs. With <tt>:missing=>:raise</tt>, +set_fields+ and +update_fields+ will raise an error if one of the entries in the hash is missing, instead of just assigning the value to nil or whatever the hash's default value is. That allows stricter checks, similar to the :strict_param_checking setting for the default mass assignment methods.
|
|
54
|
+
|
|
55
|
+
In all of the mass assignment cases, methods starting with +set+ will set the attributes without saving the object, while methods starting with +update+ will set the attributes and then save the changes to the object.
|
|
56
|
+
|