sequel 4.24.0 → 4.25.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (54) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG +40 -0
  3. data/doc/association_basics.rdoc +2 -5
  4. data/doc/dataset_basics.rdoc +1 -1
  5. data/doc/postgresql.rdoc +47 -0
  6. data/doc/querying.rdoc +5 -0
  7. data/doc/release_notes/4.25.0.txt +181 -0
  8. data/lib/sequel/adapters/ibmdb.rb +0 -28
  9. data/lib/sequel/adapters/shared/db2.rb +31 -2
  10. data/lib/sequel/adapters/shared/mssql.rb +12 -12
  11. data/lib/sequel/adapters/shared/postgres.rb +102 -3
  12. data/lib/sequel/adapters/shared/sqlite.rb +1 -0
  13. data/lib/sequel/adapters/swift/sqlite.rb +12 -0
  14. data/lib/sequel/database/schema_generator.rb +4 -0
  15. data/lib/sequel/database/schema_methods.rb +3 -1
  16. data/lib/sequel/dataset/actions.rb +1 -1
  17. data/lib/sequel/dataset/prepared_statements.rb +15 -7
  18. data/lib/sequel/dataset/query.rb +16 -2
  19. data/lib/sequel/dataset/sql.rb +19 -16
  20. data/lib/sequel/extensions/empty_array_consider_nulls.rb +35 -0
  21. data/lib/sequel/extensions/empty_array_ignore_nulls.rb +3 -34
  22. data/lib/sequel/extensions/pg_json_ops.rb +9 -1
  23. data/lib/sequel/extensions/query_literals.rb +1 -1
  24. data/lib/sequel/model/base.rb +7 -11
  25. data/lib/sequel/model/dataset_module.rb +1 -1
  26. data/lib/sequel/plugins/association_pks.rb +6 -0
  27. data/lib/sequel/plugins/dirty.rb +6 -1
  28. data/lib/sequel/plugins/inverted_subsets.rb +48 -0
  29. data/lib/sequel/plugins/serialization.rb +2 -0
  30. data/lib/sequel/plugins/singular_table_names.rb +31 -0
  31. data/lib/sequel/plugins/static_cache.rb +17 -0
  32. data/lib/sequel/sql.rb +1 -0
  33. data/lib/sequel/version.rb +1 -1
  34. data/spec/adapters/db2_spec.rb +12 -0
  35. data/spec/adapters/mysql_spec.rb +1 -0
  36. data/spec/adapters/postgres_spec.rb +41 -1
  37. data/spec/core/database_spec.rb +1 -0
  38. data/spec/core/dataset_spec.rb +55 -7
  39. data/spec/core/expression_filters_spec.rb +18 -0
  40. data/spec/core/schema_spec.rb +10 -2
  41. data/spec/extensions/association_pks_spec.rb +12 -0
  42. data/spec/extensions/{empty_array_ignore_nulls_spec.rb → empty_array_consider_nulls_spec.rb} +7 -7
  43. data/spec/extensions/inverted_subsets_spec.rb +33 -0
  44. data/spec/extensions/query_literals_spec.rb +16 -0
  45. data/spec/extensions/serialization_spec.rb +21 -0
  46. data/spec/extensions/singular_table_names_spec.rb +22 -0
  47. data/spec/integration/dataset_test.rb +2 -1
  48. data/spec/integration/prepared_statement_test.rb +35 -1
  49. data/spec/model/associations_spec.rb +2 -2
  50. data/spec/model/base_spec.rb +13 -8
  51. data/spec/model/class_dataset_methods_spec.rb +1 -0
  52. metadata +10 -5
  53. data/lib/sequel/adapters/firebird.rb +0 -105
  54. data/lib/sequel/adapters/informix.rb +0 -68
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 1ce66a463879671227d5446f7e224b1610bccd9f
4
- data.tar.gz: e16b849b789b960f5c6d86dd7049a61ebe42c169
3
+ metadata.gz: 5bb525327915d4e6d6e8306e9edd0dc6cd32afa3
4
+ data.tar.gz: b64f5447c918b9d36b47622629ec697286adc0b8
5
5
  SHA512:
6
- metadata.gz: 3ac3191f57bffb08c000deef706301c4b6628cb707ef9f870df162d7d55d3ed21982f931c3b9bbc3658cf4a693e7aa2b45d8a3dd1c62a0345d9d2d88dd7dc391
7
- data.tar.gz: d05096b10746ea930ecd79f8cde66e295b9b5e99002c64df479369473a1bb603b36c9a69ce2462fecd33c1dc3217705bac651d590dca4c58a85edd44b1c515b3
6
+ metadata.gz: caa13716ae448d4a3b3c6f4886c2e529f495e843eeb5386b85a264d259bb54d0ffefca3d7cba9c82013d1c96c87bff8691e460e1e0a06806bb64cef18950e284
7
+ data.tar.gz: 302d93a18b52e0810e74fce6f3d4a87f497f4199fb47045834aecbe193f6796fd910453b0c1669b8d82b3d698ac5bb13346fce825311da03c7a77ab7d89d728c
data/CHANGELOG CHANGED
@@ -1,3 +1,43 @@
1
+ === 4.25.0 (2015-08-01)
2
+
3
+ * Add Dataset#insert_conflict on PostgreSQL 9.5+, for upsert/insert ignore support using INSERT ON CONFLICT (jeremyevans)
4
+
5
+ * Support Dataset#group_rollup and #group_cube on PostgreSQL 9.5+ (jeremyevans)
6
+
7
+ * Automatically REORG tables when altering when using jdbc/db2 (karlhe) (#1054)
8
+
9
+ * Recognize constraint violation exceptions on swift/sqlite (jeremyevans)
10
+
11
+ * Recognize another check constraint violation exception message on SQLite (jeremyevans)
12
+
13
+ * Allow =~ and !~ to be used on ComplexExpressions (janko-m) (#1050)
14
+
15
+ * Support case sensitive SQL Server 2012 in MSSQL metadata queries (knut2) (#1049)
16
+
17
+ * Add Dataset#group_append, for appending to the existing GROUP BY clause (YorickPeterse) (#1047)
18
+
19
+ * Add inverted_subsets plugin, for creating an inverted subset method for each subset (celsworth) (#1042)
20
+
21
+ * Make Dataset#for_update not use the :read_only database when the dataset is executed (jeremyevans) (#1041)
22
+
23
+ * Add singular_table_names plugin, for changing Sequel to not pluralize table names by default (jeremyevans)
24
+
25
+ * PreparedStatement#prepare now raises an Error (jeremyevans)
26
+
27
+ * Clear delayed association pks when refreshing an object (jeremyevans)
28
+
29
+ * Add empty_array_consider_nulls extension to make Sequel consider NULL values when using IN/NOT IN with an empty array (jeremyevans)
30
+
31
+ * Make Sequel default to ignoring NULL values when using IN/NOT IN with an empty array (jeremyevans)
32
+
33
+ * Remove the deprecated firebird and informix adapters (jeremyevans)
34
+
35
+ * Make :collate option when creating columns literalize non-String values on PostgreSQL (jeremyevans) (#1040)
36
+
37
+ * Make dirty plugin notice when serialized column is changed (celsworth) (#1039)
38
+
39
+ * Allow prepared statements to use RETURNING (jeremyevans) (#1036)
40
+
1
41
  === 4.24.0 (2015-07-01)
2
42
 
3
43
  * Allow class_table_inheritance plugin to support subclasses that don't add additional columns (QuinnHarris, jeremyevans) (#1030)
@@ -754,11 +754,8 @@ all associated objects to NULL in a single query. For +many_to_many+
754
754
  associations, this deletes all matching rows in the join table.
755
755
  Unlike the add_<i>association</i> and remove_<i>association</i> method, the
756
756
  plural form of the association name is used in this method.
757
- The remove_all_<i>association</i> method returns the number of rows updated
758
- for +one_to_many+ associations and the number of rows deleted for
759
- +many_to_many+ associations:
760
-
761
- @rows_modified = @artist.remove_all_albums
757
+ The remove_all_<i>association</i> method returns the previously cached associated
758
+ records, or nil if there were no cached associated records.
762
759
 
763
760
  === <i>association</i>_dataset (e.g. albums_dataset)
764
761
 
@@ -78,7 +78,7 @@ 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
80
  WHERE:: where, filter, exclude, exclude_where, and, or, grep, invert, unfiltered
81
- GROUP:: group, group_by, group_and_count, select_group, ungrouped
81
+ GROUP:: group, group_by, group_and_count, group_append, select_group, ungrouped
82
82
  HAVING:: having, exclude_having, invert, unfiltered
83
83
  ORDER:: order, order_by, order_append, order_prepend, order_more, reverse, reverse_order, unordered
84
84
  LIMIT/OFFSET:: limit, offset, unlimited
data/doc/postgresql.rdoc CHANGED
@@ -185,6 +185,53 @@ When returning is used, instead of returning the number of rows affected (for up
185
185
  or the serial primary key value (for insert), it will return an array of hashes with the
186
186
  returned results.
187
187
 
188
+ === INSERT ON CONFLICT Support
189
+
190
+ Starting with PostgreSQL 9.5, you can do an upsert or ignore unique or exclusion constraint
191
+ violations when inserting using <tt>Dataset#insert_conflict</tt>:
192
+
193
+ DB[:table].insert_conflict.insert(:a=>1, :b=>2)
194
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
195
+ # ON CONFLICT DO NOTHING
196
+
197
+ For compatibility with Sequel's MySQL support, you can also use +insert_ignore+:
198
+
199
+ DB[:table].insert_ignore.insert(:a=>1, :b=>2)
200
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
201
+ # ON CONFLICT DO NOTHING
202
+
203
+ You can pass a specific constraint name using +:constraint+, to only ignore a specific
204
+ constraint violation:
205
+
206
+ DB[:table].insert_conflict(:constraint=>:table_a_uidx).insert(:a=>1, :b=>2)
207
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
208
+ # ON CONFLICT ON CONSTRAINT table_a_uidx DO NOTHING
209
+
210
+ If the unique or exclusion constraint covers the whole table (e.g. it isn't a partial unique
211
+ index), then you can just specify the column using the +:target+ option:
212
+
213
+ DB[:table].insert_conflict(:target=>:a).insert(:a=>1, :b=>2)
214
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
215
+ # ON CONFLICT (a) DO NOTHING
216
+
217
+ If you want to update the existing row instead of ignoring the constraint violation, you
218
+ can pass an +:update+ option with a hash of values to update. You must pass either the
219
+ +:target+ or +:constraint+ options when passing the +:update+ option:
220
+
221
+ DB[:table].insert_conflict(:target=>:a, :update=>{:b=>:excluded__b}).insert(:a=>1, :b=>2)
222
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
223
+ # ON CONFLICT (a) DO UPDATE SET b = excluded.b
224
+
225
+ Additionally, if you only want to do the update in certain cases, you can specify an
226
+ +:update_where+ option, which will be used as a filter. If the row doesn't match the
227
+ conditions, the constraint violation will be ignored, but the row will not be updated:
228
+
229
+ DB[:table].insert_conflict(:constraint=>:table_a_uidx,
230
+ :update=>{:b=>:excluded__b}, :update_where=>{:table__status_id=>1}).insert(:a=>1, :b=>2)
231
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
232
+ # ON CONFLICT ON CONSTRAINT table_a_uidx
233
+ # DO UPDATE SET b = excluded.b WHERE (table.status_id = 1)
234
+
188
235
  === Distinct On Specific Columns
189
236
 
190
237
  Sequel allows passing columns to <tt>Dataset#distinct</tt>, which will make the dataset return
data/doc/querying.rdoc CHANGED
@@ -677,6 +677,11 @@ You can remove an existing grouping using +ungrouped+:
677
677
 
678
678
  Album.group(:artist_id).ungrouped
679
679
  # SELECT * FROM albums
680
+
681
+ If you want to add a column to the end of the existing grouping columns:
682
+
683
+ Album.group(:artist_id).group_append(:name)
684
+ # SELECT * FROM albums GROUP BY artist_id, name
680
685
 
681
686
  A common use of grouping is to count based on the number of grouped rows,
682
687
  and Sequel provides a +group_and_count+ method to make this easier:
@@ -0,0 +1,181 @@
1
+ = New Features
2
+
3
+ * The =~ and !~ methods are now defined on ComplexExpressions in
4
+ addition to GenericExpressions, allowing the following code to
5
+ work:
6
+
7
+ DB[:table].where{(column1 + column2) =~ column3}
8
+
9
+ * Dataset#group_append has been added for appending to an existing
10
+ GROUP BY clause:
11
+
12
+ ds = DB[:table].group(:column1)
13
+ # SELECT * FROM table GROUP BY column1
14
+
15
+ ds = ds.group_append(:column2)
16
+ # SELECT * FROM table GROUP BY column1, column2
17
+
18
+ * An inverted_subsets plugin has been added, for automatic creation of
19
+ methods for the inversion of the subset criteria. For example:
20
+
21
+ Album.plugin :inverted_subsets
22
+ Album.subset :published, :published=>true
23
+
24
+ Album.published
25
+ # SELECT * FROM albums WHERE published IS TRUE
26
+
27
+ Album.not_published
28
+ # SELECT * FROM albums WHERE published IS NOT TRUE
29
+
30
+ By default, the subset method name is prefixed with "not_". You can
31
+ pass a block to override the default behavior:
32
+
33
+ Album.plugin(:inverted_subsets){|name| "exclude_#{name}"}
34
+ Album.subset :published, :published=>true
35
+
36
+ Album.exclude_published
37
+ # SELECT * FROM albums WHERE published IS NOT TRUE
38
+
39
+ * A singular_table_names plugin has been added, which changes Sequel
40
+ to not pluralize table names by default.
41
+
42
+ Sequel::Model.plugin :singular_table_names
43
+ class FooBar < Sequel::Model; end
44
+ FooBar.table_name # => foo_bar
45
+
46
+ * Dataset#insert_conflict and #insert_ignore have been added on
47
+ PostgreSQL. When using PostgreSQL 9.5+, they allow you to ignore
48
+ unique or exclusion constraint violations on inserting, or to do
49
+ an update instead:
50
+
51
+ DB[:table].insert_conflict.insert(:a=>1, :b=>2)
52
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
53
+ # ON CONFLICT DO NOTHING
54
+
55
+ You can pass a specific constraint name using :constraint, to only
56
+ ignore a specific constraint violation:
57
+
58
+ DB[:table].insert_conflict(:constraint=>:table_a_uidx).
59
+ insert(:a=>1, :b=>2)
60
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
61
+ # ON CONFLICT ON CONSTRAINT table_a_uidx DO NOTHING
62
+
63
+ If the unique or exclusion constraint covers the whole table (e.g.
64
+ it isn't a partial unique index), then you can just specify the
65
+ column using the :target option:
66
+
67
+ DB[:table].insert_conflict(:target=>:a).insert(:a=>1, :b=>2)
68
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
69
+ # ON CONFLICT (a) DO NOTHING
70
+
71
+ If you want to update the existing row instead of ignoring the
72
+ constraint violation, you can pass an :update option with a hash of
73
+ values to update. You must pass either the :target or :constraint
74
+ options when passing the :update option:
75
+
76
+ DB[:table].insert_conflict(:target=>:a,
77
+ :update=>{:b=>:excluded__b}).
78
+ insert(:a=>1, :b=>2)
79
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
80
+ # ON CONFLICT (a) DO UPDATE SET b = excluded.b
81
+
82
+ Additionally, if you only want to do the update in certain cases,
83
+ you can specify an :update_where option, which will be used as a
84
+ filter. If the row doesn't match the conditions, the constraint
85
+ violation will be ignored, but the row will not be updated:
86
+
87
+ DB[:table].insert_conflict(:constraint=>:table_a_uidx,
88
+ :update=>{:b=>:excluded__b},
89
+ :update_where=>{:table__status_id=>1}).
90
+ insert(:a=>1, :b=>2)
91
+ # INSERT INTO TABLE (a, b) VALUES (1, 2)
92
+ # ON CONFLICT ON CONSTRAINT table_a_uidx
93
+ # DO UPDATE SET b = excluded.b WHERE (table.status_id = 1)
94
+
95
+ * Dataset#group_rollup and #group_cube are now supported when using
96
+ PostgreSQL 9.5+.
97
+
98
+ * Sequel now supports Dataset#returning when using prepared statements
99
+ and bound variables:
100
+
101
+ DB[:table].returning.prepare(:insert, :i, :col=>:$col).
102
+ call(:col=>42)
103
+ # => [{:col=>42}]
104
+
105
+ = Other Improvements
106
+
107
+ * The serialization plugin now integrates with the dirty plugin, so
108
+ that column changes are detected correctly. However, column values
109
+ that are changed and then changed back to the original value are
110
+ still detected as changed.
111
+
112
+ * Dataset#for_update and similar locking methods now cause Sequel not
113
+ to use the :read_only shard if sharding is used.
114
+
115
+ * The association_pks plugin now clears cached delayed associated pks
116
+ when the object is refreshed.
117
+
118
+ * The :collate column option when adding columns now literalizes
119
+ non-String values on PostgreSQL. Previously, the :collate option
120
+ value was used verbatim. This is because PostgreSQL's collations
121
+ generally require quoting as they are uppercase or mixed-case.
122
+
123
+ * Sequel's metadata parsing methods now support Microsoft SQL Server
124
+ 2012+ when used in case sensitive mode.
125
+
126
+ * Sequel now recognizes an addition check constraint violation
127
+ exception on SQLite.
128
+
129
+ * Sequel now recognizes constraint violations when using the
130
+ swift/sqlite adapter.
131
+
132
+ * Sequel now automatically REORGs tables when altering them in the
133
+ jdbc/db2 adapter.
134
+
135
+ = Backwards Compatibility
136
+
137
+ * Sequel now defaults to ignoring NULL values when using IN/NOT IN
138
+ with an empty array. Previously, code such as:
139
+
140
+ DB[:table].where(:column=>[])
141
+
142
+ would be literalized as:
143
+
144
+ SELECT * FROM table WHERE (column != column)
145
+
146
+ This yields a NULL value when column is NULL, similarly to how most
147
+ other SQL operators work. Unfortunately, most databases do not
148
+ optimize this, and such a query can require a sequential scan of the
149
+ table.
150
+
151
+ Sequel previously shipped with a empty_array_ignore_nulls extension
152
+ that literalized the query to:
153
+
154
+ SELECT * FROM table WHERE (1 = 0)
155
+
156
+ which databases will generally optimize to a constant false value,
157
+ resulting in much faster queries. This behavior is now the default.
158
+
159
+ Users that desire the previous behavior can use the new
160
+ empty_array_consider_nulls extension.
161
+
162
+ * The deprecated firebird and informix adapters have been removed.
163
+
164
+ * Calling prepare on a prepared statement now raises an exception.
165
+ It was supported accidently before, as prepared statements are
166
+ dataset instances.
167
+
168
+ * Model::DatasetModule#subset now calls Model.subset instead of
169
+ the other way around. This makes it possible to modify the
170
+ behavior of subset in a plugin.
171
+
172
+ * The :collate column option change on PostgreSQL can break code
173
+ that used already quoted values in symbols. For example:
174
+
175
+ String :column_name, collate=>:'"C"'
176
+
177
+ would need to change to:
178
+
179
+ String :column_name, collate=>:C
180
+ # or
181
+ String :column_name, collate=>'"C"'
@@ -185,15 +185,6 @@ module Sequel
185
185
 
186
186
  # Hash of connection procs for converting
187
187
  attr_reader :conversion_procs
188
-
189
- # REORG the related table whenever it is altered. This is not always
190
- # required, but it is necessary for compatibilty with other Sequel
191
- # code in many cases.
192
- def alter_table(name, generator=nil)
193
- res = super
194
- reorg(name)
195
- res
196
- end
197
188
 
198
189
  # Create a new connection object for the given server.
199
190
  def connect(server)
@@ -271,25 +262,6 @@ module Sequel
271
262
  end
272
263
  end
273
264
 
274
- # On DB2, a table might need to be REORGed if you are testing existence
275
- # of it. This REORGs automatically if the database raises a specific
276
- # error that indicates it should be REORGed.
277
- def table_exists?(name)
278
- v ||= false # only retry once
279
- sch, table_name = schema_and_table(name)
280
- name = SQL::QualifiedIdentifier.new(sch, table_name) if sch
281
- from(name).first
282
- true
283
- rescue DatabaseError => e
284
- if e.to_s =~ /Operation not allowed for reason code "7" on table/ && v == false
285
- # table probably needs reorg
286
- reorg(name)
287
- v = true
288
- retry
289
- end
290
- false
291
- end
292
-
293
265
  private
294
266
 
295
267
  # Execute the given SQL on the database.
@@ -83,6 +83,25 @@ module Sequel
83
83
  true
84
84
  end
85
85
 
86
+ # On DB2, a table might need to be REORGed if you are testing existence
87
+ # of it. This REORGs automatically if the database raises a specific
88
+ # error that indicates it should be REORGed.
89
+ def table_exists?(name)
90
+ v ||= false # only retry once
91
+ sch, table_name = schema_and_table(name)
92
+ name = SQL::QualifiedIdentifier.new(sch, table_name) if sch
93
+ from(name).first
94
+ true
95
+ rescue DatabaseError => e
96
+ if e.to_s =~ /Operation not allowed for reason code "7" on table/ && v == false
97
+ # table probably needs reorg
98
+ reorg(name)
99
+ v = true
100
+ retry
101
+ end
102
+ false
103
+ end
104
+
86
105
  private
87
106
 
88
107
  # Handle DB2 specific alter table operations.
@@ -119,6 +138,16 @@ module Sequel
119
138
  end
120
139
  end
121
140
 
141
+ # REORG the related table whenever it is altered. This is not always
142
+ # required, but it is necessary for compatibilty with other Sequel
143
+ # code in many cases.
144
+ def apply_alter_table(name, ops)
145
+ alter_table_sql_list(name, ops).each do |sql|
146
+ execute_ddl(sql)
147
+ reorg(name)
148
+ end
149
+ end
150
+
122
151
  # DB2 uses an identity column for autoincrement.
123
152
  def auto_increment_sql
124
153
  AUTOINCREMENT
@@ -190,12 +219,12 @@ module Sequel
190
219
  # Run the REORG TABLE command for the table, necessary when
191
220
  # the table has been altered.
192
221
  def reorg(table)
193
- synchronize(opts[:server]){|c| c.execute(reorg_sql(table))}
222
+ execute_ddl(reorg_sql(table))
194
223
  end
195
224
 
196
225
  # The SQL to use for REORGing a table.
197
226
  def reorg_sql(table)
198
- "CALL ADMIN_CMD(#{literal("REORG TABLE #{table}")})"
227
+ "CALL SYSPROC.ADMIN_CMD(#{literal("REORG TABLE #{quote_schema_table(table)}")})"
199
228
  end
200
229
 
201
230
  # Treat clob as blob if use_clob_as_blob is true
@@ -131,10 +131,10 @@ module Sequel
131
131
  schema, table = schema_and_table(table)
132
132
  current_schema = m.call(get(Sequel.function('schema_name')))
133
133
  fk_action_map = FOREIGN_KEY_ACTION_MAP
134
- ds = metadata_dataset.from(:sys__foreign_keys___fk).
135
- join(:sys__foreign_key_columns___fkc, :constraint_object_id => :object_id).
136
- join(:sys__all_columns___pc, :object_id => :fkc__parent_object_id, :column_id => :fkc__parent_column_id).
137
- join(:sys__all_columns___rc, :object_id => :fkc__referenced_object_id, :column_id => :fkc__referenced_column_id).
134
+ ds = metadata_dataset.from(Sequel.lit('[sys].[foreign_keys]').as(:fk)).
135
+ join(Sequel.lit('[sys].[foreign_key_columns]').as(:fkc), :constraint_object_id => :object_id).
136
+ join(Sequel.lit('[sys].[all_columns]').as(:pc), :object_id => :fkc__parent_object_id, :column_id => :fkc__parent_column_id).
137
+ join(Sequel.lit('[sys].[all_columns]').as(:rc), :object_id => :fkc__referenced_object_id, :column_id => :fkc__referenced_column_id).
138
138
  where{{object_schema_name(:fk__parent_object_id) => im.call(schema || current_schema)}}.
139
139
  where{{object_name(:fk__parent_object_id) => im.call(table)}}.
140
140
  select{[:fk__name,
@@ -169,10 +169,10 @@ module Sequel
169
169
  m = output_identifier_meth
170
170
  im = input_identifier_meth
171
171
  indexes = {}
172
- ds = metadata_dataset.from(:sys__tables___t).
173
- join(:sys__indexes___i, :object_id=>:object_id).
174
- join(:sys__index_columns___ic, :object_id=>:object_id, :index_id=>:index_id).
175
- join(:sys__columns___c, :object_id=>:object_id, :column_id=>:column_id).
172
+ ds = metadata_dataset.from(Sequel.lit('[sys].[tables]').as(:t)).
173
+ join(Sequel.lit('[sys].[indexes]').as(:i), :object_id=>:object_id).
174
+ join(Sequel.lit('[sys].[index_columns]').as(:ic), :object_id=>:object_id, :index_id=>:index_id).
175
+ join(Sequel.lit('[sys].[columns]').as(:c), :object_id=>:object_id, :column_id=>:column_id).
176
176
  select(:i__name, :i__is_unique, :c__name___column).
177
177
  where{{t__name=>im.call(table)}}.
178
178
  where(:i__is_primary_key=>0, :i__is_disabled=>0).
@@ -433,15 +433,15 @@ module Sequel
433
433
  inf_sch_qual = lambda{|s| info_sch_sch ? Sequel.qualify(info_sch_sch, s) : Sequel.expr(s)}
434
434
  sys_qual = lambda{|s| info_sch_sch ? Sequel.qualify(info_sch_sch, Sequel.qualify(Sequel.lit(''), s)) : Sequel.expr(s)}
435
435
 
436
- identity_cols = metadata_dataset.from(:sys__columns).
436
+ identity_cols = metadata_dataset.from(Sequel.lit('[sys].[columns]')).
437
437
  where(:object_id=>table_id, :is_identity=>true).
438
438
  select_map(:name)
439
439
 
440
- pk_index_id = metadata_dataset.from(sys_qual.call(:sysindexes)).
440
+ pk_index_id = metadata_dataset.from(sys_qual.call(Sequel.lit('sysindexes'))).
441
441
  where(:id=>table_id, :indid=>1..254){{(status & 2048)=>2048}}.
442
442
  get(:indid)
443
- pk_cols = metadata_dataset.from(sys_qual.call(:sysindexkeys).as(:sik)).
444
- join(sys_qual.call(:syscolumns).as(:sc), :id=>:id, :colid=>:colid).
443
+ pk_cols = metadata_dataset.from(sys_qual.call(Sequel.lit('sysindexkeys')).as(:sik)).
444
+ join(sys_qual.call(Sequel.lit('syscolumns')).as(:sc), :id=>:id, :colid=>:colid).
445
445
  where(:sik__id=>table_id, :sik__indid=>pk_index_id).
446
446
  select_order_map(:sc__name)
447
447