sequel 4.34.0 → 4.35.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG +30 -0
- data/Rakefile +14 -17
- data/doc/object_model.rdoc +4 -4
- data/doc/release_notes/4.35.0.txt +130 -0
- data/doc/schema_modification.rdoc +8 -3
- data/doc/security.rdoc +3 -3
- data/lib/sequel/adapters/ado.rb +2 -2
- data/lib/sequel/adapters/ado/access.rb +6 -6
- data/lib/sequel/adapters/ado/mssql.rb +2 -2
- data/lib/sequel/adapters/amalgalite.rb +6 -6
- data/lib/sequel/adapters/cubrid.rb +4 -4
- data/lib/sequel/adapters/do.rb +2 -2
- data/lib/sequel/adapters/do/mysql.rb +1 -1
- data/lib/sequel/adapters/do/postgres.rb +1 -1
- data/lib/sequel/adapters/do/sqlite3.rb +1 -1
- data/lib/sequel/adapters/ibmdb.rb +6 -6
- data/lib/sequel/adapters/jdbc.rb +15 -15
- data/lib/sequel/adapters/jdbc/db2.rb +1 -1
- data/lib/sequel/adapters/jdbc/derby.rb +3 -3
- data/lib/sequel/adapters/jdbc/h2.rb +3 -3
- data/lib/sequel/adapters/jdbc/hsqldb.rb +2 -2
- data/lib/sequel/adapters/jdbc/mssql.rb +1 -1
- data/lib/sequel/adapters/jdbc/mysql.rb +1 -1
- data/lib/sequel/adapters/jdbc/oracle.rb +1 -1
- data/lib/sequel/adapters/jdbc/postgresql.rb +2 -2
- data/lib/sequel/adapters/jdbc/sqlanywhere.rb +1 -1
- data/lib/sequel/adapters/jdbc/sqlite.rb +1 -1
- data/lib/sequel/adapters/jdbc/transactions.rb +10 -10
- data/lib/sequel/adapters/mock.rb +1 -1
- data/lib/sequel/adapters/mysql.rb +2 -2
- data/lib/sequel/adapters/mysql2.rb +2 -2
- data/lib/sequel/adapters/odbc.rb +2 -2
- data/lib/sequel/adapters/odbc/mssql.rb +2 -2
- data/lib/sequel/adapters/oracle.rb +9 -9
- data/lib/sequel/adapters/postgres.rb +3 -3
- data/lib/sequel/adapters/shared/mssql.rb +36 -8
- data/lib/sequel/adapters/shared/oracle.rb +15 -0
- data/lib/sequel/adapters/shared/postgres.rb +22 -1
- data/lib/sequel/adapters/sqlanywhere.rb +1 -1
- data/lib/sequel/adapters/sqlite.rb +7 -7
- data/lib/sequel/adapters/swift.rb +3 -3
- data/lib/sequel/adapters/swift/mysql.rb +1 -1
- data/lib/sequel/adapters/swift/postgres.rb +1 -1
- data/lib/sequel/adapters/swift/sqlite.rb +1 -1
- data/lib/sequel/adapters/tinytds.rb +5 -7
- data/lib/sequel/database/logging.rb +18 -3
- data/lib/sequel/database/misc.rb +19 -8
- data/lib/sequel/database/schema_generator.rb +7 -2
- data/lib/sequel/database/schema_methods.rb +9 -2
- data/lib/sequel/database/transactions.rb +52 -18
- data/lib/sequel/dataset/actions.rb +24 -19
- data/lib/sequel/dataset/features.rb +5 -0
- data/lib/sequel/dataset/query.rb +6 -0
- data/lib/sequel/extensions/_pretty_table.rb +1 -1
- data/lib/sequel/extensions/error_sql.rb +3 -3
- data/lib/sequel/extensions/pg_range.rb +10 -1
- data/lib/sequel/extensions/schema_dumper.rb +8 -5
- data/lib/sequel/extensions/server_logging.rb +61 -0
- data/lib/sequel/extensions/sql_comments.rb +91 -0
- data/lib/sequel/model/associations.rb +40 -8
- data/lib/sequel/model/base.rb +19 -5
- data/lib/sequel/plugins/class_table_inheritance.rb +12 -0
- data/lib/sequel/plugins/delay_add_association.rb +1 -0
- data/lib/sequel/plugins/json_serializer.rb +10 -2
- data/lib/sequel/version.rb +1 -1
- data/spec/adapter_spec.rb +4 -0
- data/spec/adapters/mysql_spec.rb +1 -1
- data/spec/adapters/postgres_spec.rb +3 -2
- data/spec/core/connection_pool_spec.rb +2 -0
- data/spec/core/database_spec.rb +49 -0
- data/spec/core/dataset_spec.rb +25 -1
- data/spec/core/mock_adapter_spec.rb +3 -1
- data/spec/core/schema_generator_spec.rb +1 -1
- data/spec/core_model_spec.rb +2 -0
- data/spec/core_spec.rb +1 -0
- data/spec/extensions/delay_add_association_spec.rb +22 -0
- data/spec/extensions/json_serializer_spec.rb +6 -0
- data/spec/extensions/pg_range_spec.rb +30 -2
- data/spec/extensions/schema_dumper_spec.rb +3 -2
- data/spec/extensions/server_logging_spec.rb +45 -0
- data/spec/extensions/sql_comments_spec.rb +27 -0
- data/spec/files/reversible_migrations/006_reversible.rb +10 -0
- data/spec/files/reversible_migrations/007_reversible.rb +10 -0
- data/spec/integration/dataset_test.rb +28 -2
- data/spec/integration/migrator_test.rb +23 -1
- data/spec/integration/schema_test.rb +12 -32
- data/spec/integration/transaction_test.rb +10 -0
- data/spec/integration/type_test.rb +1 -1
- data/spec/model/eager_loading_spec.rb +16 -0
- data/spec/model/record_spec.rb +9 -0
- data/spec/model_no_assoc_spec.rb +1 -0
- data/spec/model_spec.rb +1 -0
- data/spec/plugin_spec.rb +1 -0
- metadata +16 -2
@@ -24,9 +24,9 @@ module Sequel
|
|
24
24
|
def execute_insert(sql, opts=OPTS)
|
25
25
|
synchronize(opts[:server]) do |conn|
|
26
26
|
begin
|
27
|
-
|
27
|
+
log_connection_yield(sql, conn){conn.do(sql)}
|
28
28
|
begin
|
29
|
-
s =
|
29
|
+
s = log_connection_yield(LAST_INSERT_ID_SQL, conn){conn.run(LAST_INSERT_ID_SQL)}
|
30
30
|
if (rows = s.fetch_all) and (row = rows.first) and (v = row.first)
|
31
31
|
Integer(v)
|
32
32
|
end
|
@@ -80,10 +80,10 @@ module Sequel
|
|
80
80
|
if args = opts[:arguments]
|
81
81
|
r = conn.parse(sql)
|
82
82
|
args = cursor_bind_params(conn, r, args)
|
83
|
-
nr =
|
83
|
+
nr = log_connection_yield(sql, conn, args){r.exec}
|
84
84
|
r = nr unless block_given?
|
85
85
|
else
|
86
|
-
r =
|
86
|
+
r = log_connection_yield(sql, conn){conn.exec(sql)}
|
87
87
|
end
|
88
88
|
if block_given?
|
89
89
|
begin
|
@@ -172,7 +172,7 @@ module Sequel
|
|
172
172
|
end
|
173
173
|
end
|
174
174
|
unless cursor
|
175
|
-
cursor =
|
175
|
+
cursor = log_connection_yield("PREPARE #{name}: #{sql}", conn){conn.parse(sql)}
|
176
176
|
conn.prepared_statements[name] = [cursor, sql]
|
177
177
|
end
|
178
178
|
args = cursor_bind_params(conn, cursor, opts[:arguments])
|
@@ -182,7 +182,7 @@ module Sequel
|
|
182
182
|
log_sql << sql
|
183
183
|
log_sql << ")"
|
184
184
|
end
|
185
|
-
r =
|
185
|
+
r = log_connection_yield(log_sql, conn, args){cursor.exec}
|
186
186
|
if block_given?
|
187
187
|
yield(cursor)
|
188
188
|
elsif type == :insert
|
@@ -201,7 +201,7 @@ module Sequel
|
|
201
201
|
if sequence
|
202
202
|
sql = "SELECT #{literal(sequence)}.currval FROM dual"
|
203
203
|
begin
|
204
|
-
cursor =
|
204
|
+
cursor = log_connection_yield(sql, conn){conn.exec(sql)}
|
205
205
|
row = cursor.fetch
|
206
206
|
row.each{|v| return (v.to_i if v)}
|
207
207
|
rescue OCIError
|
@@ -213,12 +213,12 @@ module Sequel
|
|
213
213
|
end
|
214
214
|
|
215
215
|
def begin_transaction(conn, opts=OPTS)
|
216
|
-
|
216
|
+
log_connection_yield(TRANSACTION_BEGIN, conn){conn.autocommit = false}
|
217
217
|
set_transaction_isolation(conn, opts)
|
218
218
|
end
|
219
219
|
|
220
220
|
def commit_transaction(conn, opts=OPTS)
|
221
|
-
|
221
|
+
log_connection_yield(TRANSACTION_COMMIT, conn){conn.commit}
|
222
222
|
end
|
223
223
|
|
224
224
|
def disconnect_error?(e, opts)
|
@@ -250,7 +250,7 @@ module Sequel
|
|
250
250
|
end
|
251
251
|
|
252
252
|
def rollback_transaction(conn, opts=OPTS)
|
253
|
-
|
253
|
+
log_connection_yield(TRANSACTION_ROLLBACK, conn){conn.rollback}
|
254
254
|
end
|
255
255
|
|
256
256
|
def schema_parse_table(table, opts=OPTS)
|
@@ -283,7 +283,7 @@ module Sequel
|
|
283
283
|
|
284
284
|
metadata = synchronize(opts[:server]) do |conn|
|
285
285
|
begin
|
286
|
-
|
286
|
+
log_connection_yield("Connection.describe_table", conn){conn.describe_table(schema_and_table)}
|
287
287
|
rescue OCIError => e
|
288
288
|
raise_error(e)
|
289
289
|
end
|
@@ -183,7 +183,7 @@ module Sequel
|
|
183
183
|
# Return the PGResult object that is returned by executing the given
|
184
184
|
# sql and args.
|
185
185
|
def execute_query(sql, args)
|
186
|
-
@db.
|
186
|
+
@db.log_connection_yield(sql, self, args){args ? async_exec(sql, args) : async_exec(sql)}
|
187
187
|
end
|
188
188
|
end
|
189
189
|
|
@@ -584,7 +584,7 @@ module Sequel
|
|
584
584
|
|
585
585
|
unless conn.prepared_statements[ps_name] == sql
|
586
586
|
conn.execute("DEALLOCATE #{ps_name}") if conn.prepared_statements.include?(ps_name)
|
587
|
-
conn.check_disconnect_errors{
|
587
|
+
conn.check_disconnect_errors{log_connection_yield("PREPARE #{ps_name} AS #{sql}", conn){conn.prepare(ps_name, sql)}}
|
588
588
|
conn.prepared_statements[ps_name] = sql
|
589
589
|
end
|
590
590
|
|
@@ -595,7 +595,7 @@ module Sequel
|
|
595
595
|
log_sql << ")"
|
596
596
|
end
|
597
597
|
|
598
|
-
q = conn.check_disconnect_errors{
|
598
|
+
q = conn.check_disconnect_errors{log_connection_yield(log_sql, conn, args){_execute_prepared_statement(conn, ps_name, args, opts)}}
|
599
599
|
begin
|
600
600
|
block_given? ? yield(q) : q.cmd_tuples
|
601
601
|
ensure
|
@@ -516,8 +516,10 @@ module Sequel
|
|
516
516
|
BOOL_TRUE = '1'.freeze
|
517
517
|
BOOL_FALSE = '0'.freeze
|
518
518
|
COMMA_SEPARATOR = ', '.freeze
|
519
|
-
|
520
|
-
|
519
|
+
TABLE_HINT = " WITH (".freeze
|
520
|
+
READPAST = "READPAST".freeze
|
521
|
+
NOLOCK = 'NOLOCK'.freeze
|
522
|
+
UPDLOCK = 'UPDLOCK'.freeze
|
521
523
|
WILDCARD = LiteralString.new('*').freeze
|
522
524
|
CONSTANT_MAP = {:CURRENT_DATE=>'CAST(CURRENT_TIMESTAMP AS DATE)'.freeze, :CURRENT_TIME=>'CAST(CURRENT_TIMESTAMP AS TIME)'.freeze}
|
523
525
|
EXTRACT_MAP = {:year=>"yy", :month=>"m", :day=>"d", :hour=>"hh", :minute=>"n", :second=>"s"}
|
@@ -732,7 +734,7 @@ module Sequel
|
|
732
734
|
is_2005_or_later?
|
733
735
|
end
|
734
736
|
|
735
|
-
# MSSQL
|
737
|
+
# MSSQL 2008+ supports GROUPING SETS
|
736
738
|
def supports_grouping_sets?
|
737
739
|
is_2008_or_later?
|
738
740
|
end
|
@@ -782,6 +784,11 @@ module Sequel
|
|
782
784
|
supports_insert_select?
|
783
785
|
end
|
784
786
|
|
787
|
+
# MSSQL uses READPAST to skip locked rows.
|
788
|
+
def supports_skip_locked?
|
789
|
+
true
|
790
|
+
end
|
791
|
+
|
785
792
|
# MSSQL 2005+ supports window functions
|
786
793
|
def supports_window_functions?
|
787
794
|
true
|
@@ -965,11 +972,32 @@ module Sequel
|
|
965
972
|
|
966
973
|
# Support different types of locking styles
|
967
974
|
def select_lock_sql(sql)
|
968
|
-
|
969
|
-
|
970
|
-
|
971
|
-
|
972
|
-
|
975
|
+
lock = @opts[:lock]
|
976
|
+
skip_locked = @opts[:skip_locked]
|
977
|
+
for_update = lock == :update
|
978
|
+
dirty = lock == :dirty
|
979
|
+
lock_hint = for_update || dirty
|
980
|
+
|
981
|
+
if lock_hint || skip_locked
|
982
|
+
sql << TABLE_HINT
|
983
|
+
|
984
|
+
if lock_hint
|
985
|
+
sql << if for_update
|
986
|
+
UPDLOCK
|
987
|
+
else
|
988
|
+
NOLOCK
|
989
|
+
end
|
990
|
+
end
|
991
|
+
|
992
|
+
if lock_hint && skip_locked
|
993
|
+
sql << COMMA_SEPARATOR
|
994
|
+
end
|
995
|
+
|
996
|
+
if skip_locked
|
997
|
+
sql << READPAST
|
998
|
+
end
|
999
|
+
|
1000
|
+
sql << PAREN_CLOSE
|
973
1001
|
else
|
974
1002
|
super
|
975
1003
|
end
|
@@ -287,6 +287,7 @@ module Sequel
|
|
287
287
|
HSTAR = "H*".freeze
|
288
288
|
DUAL = ' FROM DUAL'.freeze
|
289
289
|
BITAND_PROC = lambda{|a, b| Sequel.lit(["CAST(BITAND(", ", ", ") AS INTEGER)"], a, b)}
|
290
|
+
SKIP_LOCKED = " SKIP LOCKED".freeze
|
290
291
|
|
291
292
|
include(Module.new do
|
292
293
|
Dataset.def_sql_method(self, :select, %w'with select distinct columns from join where group having compounds order lock')
|
@@ -431,6 +432,11 @@ module Sequel
|
|
431
432
|
false
|
432
433
|
end
|
433
434
|
|
435
|
+
# Oracle supports SKIP LOCKED.
|
436
|
+
def supports_skip_locked?
|
437
|
+
true
|
438
|
+
end
|
439
|
+
|
434
440
|
# Oracle supports timezones in literal timestamps.
|
435
441
|
def supports_timestamp_timezones?
|
436
442
|
true
|
@@ -536,6 +542,15 @@ module Sequel
|
|
536
542
|
:union
|
537
543
|
end
|
538
544
|
|
545
|
+
# Use SKIP LOCKED if skipping locked rows.
|
546
|
+
def select_lock_sql(sql)
|
547
|
+
super
|
548
|
+
|
549
|
+
if @opts[:skip_locked]
|
550
|
+
sql << SKIP_LOCKED
|
551
|
+
end
|
552
|
+
end
|
553
|
+
|
539
554
|
# Oracle supports quoted function names.
|
540
555
|
def supports_quoted_function_names?
|
541
556
|
true
|
@@ -1214,6 +1214,7 @@ module Sequel
|
|
1214
1214
|
SELECT_VALUES = "VALUES ".freeze
|
1215
1215
|
EMPTY_STRING = ''.freeze
|
1216
1216
|
LOCK_MODES = ['ACCESS SHARE', 'ROW SHARE', 'ROW EXCLUSIVE', 'SHARE UPDATE EXCLUSIVE', 'SHARE', 'SHARE ROW EXCLUSIVE', 'EXCLUSIVE', 'ACCESS EXCLUSIVE'].each(&:freeze)
|
1217
|
+
SKIP_LOCKED = " SKIP LOCKED".freeze
|
1217
1218
|
|
1218
1219
|
Dataset.def_sql_method(self, :delete, [['if server_version >= 90100', %w'with delete from using where returning'], ['else', %w'delete from using where returning']])
|
1219
1220
|
Dataset.def_sql_method(self, :insert, [['if server_version >= 90500', %w'with insert into columns values conflict returning'], ['elsif server_version >= 90100', %w'with insert into columns values returning'], ['else', %w'insert into columns values returning']])
|
@@ -1305,6 +1306,8 @@ module Sequel
|
|
1305
1306
|
# of any of the terms in any of the cols.
|
1306
1307
|
#
|
1307
1308
|
# Options:
|
1309
|
+
# :headline :: Append a expression to the selected columns aliased to headline that
|
1310
|
+
# contains an extract of the matched text.
|
1308
1311
|
# :language :: The language to use for the search (default: 'simple')
|
1309
1312
|
# :plain :: Whether a plain search should be used (default: false). In this case,
|
1310
1313
|
# terms should be a single string, and it will do a search where cols
|
@@ -1341,6 +1344,10 @@ module Sequel
|
|
1341
1344
|
ds = ds.reverse{ts_rank_cd(cols, terms)}
|
1342
1345
|
end
|
1343
1346
|
|
1347
|
+
if opts[:headline]
|
1348
|
+
ds = ds.select_append{ts_headline(lang, phrase_cols, terms).as(:headline)}
|
1349
|
+
end
|
1350
|
+
|
1344
1351
|
ds
|
1345
1352
|
end
|
1346
1353
|
|
@@ -1504,6 +1511,11 @@ module Sequel
|
|
1504
1511
|
true
|
1505
1512
|
end
|
1506
1513
|
|
1514
|
+
# PostgreSQL 9.5+ supports SKIP LOCKED.
|
1515
|
+
def supports_skip_locked?
|
1516
|
+
server_version >= 90500
|
1517
|
+
end
|
1518
|
+
|
1507
1519
|
# PostgreSQL supports timezones in literal timestamps
|
1508
1520
|
def supports_timestamp_timezones?
|
1509
1521
|
true
|
@@ -1684,8 +1696,17 @@ module Sequel
|
|
1684
1696
|
end
|
1685
1697
|
|
1686
1698
|
# Support FOR SHARE locking when using the :share lock style.
|
1699
|
+
# Use SKIP LOCKED if skipping locked rows.
|
1687
1700
|
def select_lock_sql(sql)
|
1688
|
-
@opts[:lock] == :share
|
1701
|
+
if @opts[:lock] == :share
|
1702
|
+
sql << FOR_SHARE
|
1703
|
+
else
|
1704
|
+
super
|
1705
|
+
end
|
1706
|
+
|
1707
|
+
if @opts[:skip_locked]
|
1708
|
+
sql << SKIP_LOCKED
|
1709
|
+
end
|
1689
1710
|
end
|
1690
1711
|
|
1691
1712
|
# Support VALUES clause instead of the SELECT clause to return rows.
|
@@ -102,7 +102,7 @@ module Sequel
|
|
102
102
|
|
103
103
|
LAST_INSERT_ID = 'SELECT @@IDENTITY'.freeze
|
104
104
|
def _execute(conn, type, sql, opts)
|
105
|
-
unless rs =
|
105
|
+
unless rs = log_connection_yield(sql, conn){@api.sqlany_execute_direct(conn, sql)}
|
106
106
|
result, errstr = @api.sqlany_error(conn)
|
107
107
|
raise_error(SQLAnywhereException.new(errstr, result, sql))
|
108
108
|
end
|
@@ -109,7 +109,7 @@ module Sequel
|
|
109
109
|
db = ::SQLite3::Database.new(opts[:database].to_s, sqlite3_opts)
|
110
110
|
db.busy_timeout(opts.fetch(:timeout, 5000))
|
111
111
|
|
112
|
-
connection_pragmas.each{|s|
|
112
|
+
connection_pragmas.each{|s| log_connection_yield(s, db){db.execute_batch(s)}}
|
113
113
|
|
114
114
|
class << db
|
115
115
|
attr_reader :prepared_statements
|
@@ -184,12 +184,12 @@ module Sequel
|
|
184
184
|
opts.fetch(:arguments, {}).each{|k, v| args[k] = prepared_statement_argument(v)}
|
185
185
|
case type
|
186
186
|
when :select
|
187
|
-
|
187
|
+
log_connection_yield(sql, conn, log_args){conn.query(sql, args, &block)}
|
188
188
|
when :insert
|
189
|
-
|
189
|
+
log_connection_yield(sql, conn, log_args){conn.execute(sql, args)}
|
190
190
|
conn.last_insert_row_id
|
191
191
|
when :update
|
192
|
-
|
192
|
+
log_connection_yield(sql, conn, log_args){conn.execute_batch(sql, args)}
|
193
193
|
conn.changes
|
194
194
|
end
|
195
195
|
end
|
@@ -241,7 +241,7 @@ module Sequel
|
|
241
241
|
end
|
242
242
|
end
|
243
243
|
unless cps
|
244
|
-
cps =
|
244
|
+
cps = log_connection_yield("PREPARE #{name}: #{sql}", conn){conn.prepare(sql)}
|
245
245
|
conn.prepared_statements[name] = [cps, sql]
|
246
246
|
end
|
247
247
|
log_sql = String.new
|
@@ -252,9 +252,9 @@ module Sequel
|
|
252
252
|
log_sql << ")"
|
253
253
|
end
|
254
254
|
if block
|
255
|
-
|
255
|
+
log_connection_yield(log_sql, conn, args){cps.execute(ps_args, &block)}
|
256
256
|
else
|
257
|
-
|
257
|
+
log_connection_yield(log_sql, conn, args){cps.execute!(ps_args){|r|}}
|
258
258
|
case type
|
259
259
|
when :insert
|
260
260
|
conn.last_insert_row_id
|
@@ -50,7 +50,7 @@ module Sequel
|
|
50
50
|
def execute(sql, opts=OPTS)
|
51
51
|
synchronize(opts[:server]) do |conn|
|
52
52
|
begin
|
53
|
-
res =
|
53
|
+
res = log_connection_yield(sql, conn){conn.execute(sql)}
|
54
54
|
yield res if block_given?
|
55
55
|
nil
|
56
56
|
rescue ::Swift::Error => e
|
@@ -64,7 +64,7 @@ module Sequel
|
|
64
64
|
def execute_dui(sql, opts=OPTS)
|
65
65
|
synchronize(opts[:server]) do |conn|
|
66
66
|
begin
|
67
|
-
|
67
|
+
log_connection_yield(sql, conn){conn.execute(sql).affected_rows}
|
68
68
|
rescue ::Swift::Error => e
|
69
69
|
raise_error(e)
|
70
70
|
end
|
@@ -76,7 +76,7 @@ module Sequel
|
|
76
76
|
def execute_insert(sql, opts=OPTS)
|
77
77
|
synchronize(opts[:server]) do |conn|
|
78
78
|
begin
|
79
|
-
|
79
|
+
log_connection_yield(sql, conn){conn.execute(sql).insert_id}
|
80
80
|
rescue ::Swift::Error => e
|
81
81
|
raise_error(e)
|
82
82
|
end
|
@@ -27,7 +27,7 @@ module Sequel
|
|
27
27
|
|
28
28
|
# Apply the connectiong setting SQLs for every new connection.
|
29
29
|
def setup_connection(conn)
|
30
|
-
mysql_connection_setting_sqls.each{|sql|
|
30
|
+
mysql_connection_setting_sqls.each{|sql| log_connection_yield(sql, conn){conn.execute(sql)}}
|
31
31
|
super
|
32
32
|
end
|
33
33
|
end
|
@@ -38,7 +38,7 @@ module Sequel
|
|
38
38
|
def setup_connection(conn)
|
39
39
|
conn = super(conn)
|
40
40
|
conn.native_bind_format = true
|
41
|
-
connection_configuration_sqls.each{|sql|
|
41
|
+
connection_configuration_sqls.each{|sql| log_connection_yield(sql, conn){conn.execute(sql)}}
|
42
42
|
conn
|
43
43
|
end
|
44
44
|
end
|
@@ -18,7 +18,7 @@ module Sequel
|
|
18
18
|
|
19
19
|
if (ts = opts[:textsize])
|
20
20
|
sql = "SET TEXTSIZE #{typecast_value_integer(ts)}"
|
21
|
-
|
21
|
+
log_connection_yield(sql, c){c.execute(sql)}
|
22
22
|
end
|
23
23
|
|
24
24
|
c
|
@@ -52,12 +52,12 @@ module Sequel
|
|
52
52
|
single_value = true
|
53
53
|
end
|
54
54
|
sql = "EXEC sp_executesql N'#{c.escape(sql)}', N'#{c.escape(types.join(', '))}', #{values.join(', ')}"
|
55
|
-
|
55
|
+
log_connection_yield(sql, c) do
|
56
56
|
r = c.execute(sql)
|
57
57
|
r.each{|row| return row.values.first} if single_value
|
58
58
|
end
|
59
59
|
else
|
60
|
-
|
60
|
+
log_connection_yield(sql, c) do
|
61
61
|
r = c.execute(sql)
|
62
62
|
return r.send(m) if m
|
63
63
|
end
|
@@ -139,16 +139,14 @@ module Sequel
|
|
139
139
|
|
140
140
|
# Dispose of any possible results of execution.
|
141
141
|
def log_connection_execute(conn, sql)
|
142
|
-
|
142
|
+
log_connection_yield(sql, conn){conn.execute(sql).each}
|
143
143
|
end
|
144
144
|
|
145
145
|
# Return a 2 element array with the literal value and type to use
|
146
146
|
# in the prepared statement call for the given value and connection.
|
147
147
|
def ps_arg_type(v)
|
148
148
|
case v
|
149
|
-
when
|
150
|
-
[v, 'int']
|
151
|
-
when Bignum
|
149
|
+
when Integer
|
152
150
|
[v, 'bigint']
|
153
151
|
when Float
|
154
152
|
[v, 'double precision']
|
@@ -14,6 +14,9 @@ module Sequel
|
|
14
14
|
# Array of SQL loggers to use for this database.
|
15
15
|
attr_accessor :loggers
|
16
16
|
|
17
|
+
# Whether to include information about the connection in use when logging queries.
|
18
|
+
attr_accessor :log_connection_info
|
19
|
+
|
17
20
|
# Log level at which to log SQL queries. This is actually the method
|
18
21
|
# sent to the logger, so it should be the method name symbol. The default
|
19
22
|
# is :info, it can be set to :debug to log at DEBUG level.
|
@@ -31,9 +34,15 @@ module Sequel
|
|
31
34
|
|
32
35
|
# Yield to the block, logging any errors at error level to all loggers,
|
33
36
|
# and all other queries with the duration at warn or info level.
|
34
|
-
def log_yield(sql, args=nil)
|
37
|
+
def log_yield(sql, args=nil, &block)
|
38
|
+
log_connection_yield(sql, nil, args, &block)
|
39
|
+
end
|
40
|
+
|
41
|
+
# Yield to the block, logging any errors at error level to all loggers,
|
42
|
+
# and all other queries with the duration at warn or info level.
|
43
|
+
def log_connection_yield(sql, conn, args=nil)
|
35
44
|
return yield if @loggers.empty?
|
36
|
-
sql = "#{sql}; #{args.inspect}" if args
|
45
|
+
sql = "#{connection_info(conn) if conn && log_connection_info}#{sql}#{"; #{args.inspect}" if args}"
|
37
46
|
start = Time.now
|
38
47
|
begin
|
39
48
|
yield
|
@@ -53,11 +62,17 @@ module Sequel
|
|
53
62
|
end
|
54
63
|
|
55
64
|
private
|
65
|
+
|
66
|
+
# String including information about the connection, for use when logging
|
67
|
+
# connection info.
|
68
|
+
def connection_info(conn)
|
69
|
+
"(conn: #{conn.__id__}) "
|
70
|
+
end
|
56
71
|
|
57
72
|
# Log the given SQL and then execute it on the connection, used by
|
58
73
|
# the transaction code.
|
59
74
|
def log_connection_execute(conn, sql)
|
60
|
-
|
75
|
+
log_connection_yield(sql, conn){conn.send(connection_execute_method, sql)}
|
61
76
|
end
|
62
77
|
|
63
78
|
# Log message with message prefixed by duration at info level, or
|