activerecord-jdbc-adapter 51.8-java → 52.0-java
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -2
- data/.travis.yml +26 -51
- data/README.md +9 -11
- data/Rakefile +19 -74
- data/activerecord-jdbc-adapter.gemspec +2 -2
- data/lib/active_record/connection_adapters/mssql_adapter.rb +1 -0
- data/lib/active_record/connection_adapters/sqlserver_adapter.rb +1 -0
- data/lib/arjdbc/abstract/core.rb +2 -12
- data/lib/arjdbc/abstract/database_statements.rb +24 -10
- data/lib/arjdbc/abstract/statement_cache.rb +4 -4
- data/lib/arjdbc/db2/adapter.rb +52 -2
- data/lib/arjdbc/jdbc.rb +4 -0
- data/lib/arjdbc/jdbc/column.rb +11 -5
- data/lib/arjdbc/jdbc/connection_methods.rb +9 -2
- data/lib/arjdbc/jdbc/jdbc.rake +4 -0
- data/lib/arjdbc/mssql.rb +7 -0
- data/lib/arjdbc/mssql/adapter.rb +804 -0
- data/lib/arjdbc/mssql/column.rb +200 -0
- data/lib/arjdbc/mssql/connection_methods.rb +79 -0
- data/lib/arjdbc/mssql/explain_support.rb +99 -0
- data/lib/arjdbc/mssql/limit_helpers.rb +231 -0
- data/lib/arjdbc/mssql/lock_methods.rb +77 -0
- data/lib/arjdbc/mssql/types.rb +343 -0
- data/lib/arjdbc/mssql/utils.rb +82 -0
- data/lib/arjdbc/mysql/adapter.rb +22 -14
- data/lib/arjdbc/mysql/connection_methods.rb +9 -18
- data/lib/arjdbc/postgresql/adapter.rb +102 -75
- data/lib/arjdbc/postgresql/column.rb +3 -6
- data/lib/arjdbc/postgresql/connection_methods.rb +3 -12
- data/lib/arjdbc/postgresql/oid_types.rb +12 -86
- data/lib/arjdbc/sqlite3/adapter.rb +88 -92
- data/lib/arjdbc/sqlite3/connection_methods.rb +0 -1
- data/lib/arjdbc/tasks/database_tasks.rb +36 -16
- data/lib/arjdbc/tasks/databases.rake +75 -32
- data/lib/arjdbc/tasks/databases3.rake +215 -0
- data/lib/arjdbc/tasks/databases4.rake +39 -0
- data/lib/arjdbc/version.rb +1 -1
- data/rakelib/01-tomcat.rake +2 -2
- data/rakelib/02-test.rake +3 -0
- data/rakelib/compile.rake +70 -0
- data/rakelib/db.rake +7 -21
- data/rakelib/rails.rake +4 -5
- data/src/java/arjdbc/ArJdbcModule.java +15 -5
- data/src/java/arjdbc/derby/DerbyRubyJdbcConnection.java +2 -2
- data/src/java/arjdbc/jdbc/ConnectionFactory.java +87 -0
- data/src/java/arjdbc/jdbc/DataSourceConnectionFactory.java +1 -0
- data/src/java/arjdbc/jdbc/RubyJdbcConnection.java +29 -113
- data/src/java/arjdbc/mssql/MSSQLRubyJdbcConnection.java +14 -310
- data/src/java/arjdbc/mysql/MySQLRubyJdbcConnection.java +2 -2
- data/src/java/arjdbc/postgresql/PgResultSetMetaDataWrapper.java +23 -0
- data/src/java/arjdbc/postgresql/PostgreSQLResult.java +13 -21
- data/src/java/arjdbc/postgresql/PostgreSQLRubyJdbcConnection.java +50 -44
- data/src/java/arjdbc/util/DateTimeUtils.java +5 -141
- data/src/java/arjdbc/util/QuotingUtils.java +7 -6
- metadata +26 -11
- data/src/java/arjdbc/jdbc/RubyConnectionFactory.java +0 -61
- data/src/java/arjdbc/postgresql/PgDateTimeUtils.java +0 -52
@@ -1,7 +1,6 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
ArJdbc::ConnectionMethods.module_eval do
|
3
3
|
def postgresql_connection(config)
|
4
|
-
config = config.deep_dup
|
5
4
|
# NOTE: this isn't "really" necessary but Rails (in tests) assumes being able to :
|
6
5
|
# ActiveRecord::Base.postgresql_connection ActiveRecord::Base.configurations['arunit'].merge(:insert_returning => false)
|
7
6
|
# ... while using symbols by default but than configurations returning string keys ;(
|
@@ -17,8 +16,7 @@ ArJdbc::ConnectionMethods.module_eval do
|
|
17
16
|
::Jdbc::Postgres.load_driver(:require) if defined?(::Jdbc::Postgres.load_driver)
|
18
17
|
rescue LoadError # assuming driver.jar is on the class-path
|
19
18
|
end
|
20
|
-
driver =
|
21
|
-
defined?(::Jdbc::Postgres.driver_name) ? ::Jdbc::Postgres.driver_name : 'org.postgresql.Driver')
|
19
|
+
driver = config[:driver] ||= 'org.postgresql.Driver'
|
22
20
|
|
23
21
|
host = config[:host] ||= ( config[:hostaddr] || ENV['PGHOST'] || 'localhost' )
|
24
22
|
port = config[:port] ||= ( ENV['PGPORT'] || 5432 )
|
@@ -53,15 +51,8 @@ ArJdbc::ConnectionMethods.module_eval do
|
|
53
51
|
properties['tcpKeepAlive'] ||= config[:keepalives] if config.key?(:keepalives)
|
54
52
|
properties['kerberosServerName'] ||= config[:krbsrvname] if config[:krbsrvname]
|
55
53
|
|
56
|
-
|
57
|
-
|
58
|
-
if prepared_statements
|
59
|
-
# this makes the pgjdbc driver handle hot compatibility internally
|
60
|
-
properties['autosave'] ||= 'conservative'
|
61
|
-
else
|
62
|
-
# If prepared statements are off, lets make sure they are really *off*
|
63
|
-
properties['prepareThreshold'] = 0
|
64
|
-
end
|
54
|
+
# If prepared statements are off, lets make sure they are really *off*
|
55
|
+
properties['prepareThreshold'] ||= 0 unless config[:prepared_statements]
|
65
56
|
|
66
57
|
jdbc_connection(config)
|
67
58
|
end
|
@@ -9,61 +9,6 @@ module ArJdbc
|
|
9
9
|
# @private
|
10
10
|
OID = ::ActiveRecord::ConnectionAdapters::PostgreSQL::OID
|
11
11
|
|
12
|
-
# this version makes sure to register the types by name as well
|
13
|
-
# we still need to version with OID since it's used from SchemaStatements as well
|
14
|
-
class ArjdbcTypeMapInitializer < OID::TypeMapInitializer
|
15
|
-
private
|
16
|
-
|
17
|
-
def name_with_ns(row)
|
18
|
-
if row['in_ns']
|
19
|
-
row['typname']
|
20
|
-
else
|
21
|
-
%Q("#{row['nspname']}"."#{row['typname']}")
|
22
|
-
end
|
23
|
-
end
|
24
|
-
|
25
|
-
def register_enum_type(row)
|
26
|
-
super
|
27
|
-
register name_with_ns(row), OID::Enum.new
|
28
|
-
end
|
29
|
-
|
30
|
-
def register_array_type(row)
|
31
|
-
super
|
32
|
-
register_with_subtype(name_with_ns(row), row['typelem'].to_i) do |subtype|
|
33
|
-
OID::Array.new(subtype, row['typdelim'])
|
34
|
-
end
|
35
|
-
end
|
36
|
-
|
37
|
-
def register_range_type(row)
|
38
|
-
super
|
39
|
-
name = name_with_ns(row)
|
40
|
-
register_with_subtype(name, row['rngsubtype'].to_i) do |subtype|
|
41
|
-
OID::Range.new(subtype, name.to_sym)
|
42
|
-
end
|
43
|
-
end
|
44
|
-
|
45
|
-
def register_domain_type(row)
|
46
|
-
if base_type = @store.lookup(row['typbasetype'].to_i)
|
47
|
-
register row['oid'], base_type
|
48
|
-
register name_with_ns(row), base_type
|
49
|
-
else
|
50
|
-
warn "unknown base type (OID: #{row['typbasetype']}) for domain #{row['typname']}."
|
51
|
-
end
|
52
|
-
end
|
53
|
-
|
54
|
-
def register_composite_type(row)
|
55
|
-
if subtype = @store.lookup(row['typelem'].to_i)
|
56
|
-
register row['oid'], OID::Vector.new(row['typdelim'], subtype)
|
57
|
-
register name_with_ns(row), OID::Vector.new(row['typdelim'], subtype)
|
58
|
-
end
|
59
|
-
end
|
60
|
-
|
61
|
-
def assert_valid_registration(oid, oid_type)
|
62
|
-
ret = super
|
63
|
-
ret == 0 ? oid : ret
|
64
|
-
end
|
65
|
-
end
|
66
|
-
|
67
12
|
# @private
|
68
13
|
module OIDTypes
|
69
14
|
|
@@ -96,7 +41,7 @@ module ArJdbc
|
|
96
41
|
|
97
42
|
def get_oid_type(oid, fmod, column_name, sql_type = '') # :nodoc:
|
98
43
|
if !type_map.key?(oid)
|
99
|
-
load_additional_types(
|
44
|
+
load_additional_types([oid])
|
100
45
|
end
|
101
46
|
|
102
47
|
type_map.fetch(oid, fmod, sql_type) {
|
@@ -120,7 +65,7 @@ module ArJdbc
|
|
120
65
|
|
121
66
|
private
|
122
67
|
|
123
|
-
def initialize_type_map(m)
|
68
|
+
def initialize_type_map(m = type_map)
|
124
69
|
register_class_with_limit m, 'int2', Type::Integer
|
125
70
|
register_class_with_limit m, 'int4', Type::Integer
|
126
71
|
register_class_with_limit m, 'int8', Type::Integer
|
@@ -142,7 +87,7 @@ module ArJdbc
|
|
142
87
|
m.register_type 'bytea', OID::Bytea.new
|
143
88
|
m.register_type 'point', OID::Point.new
|
144
89
|
m.register_type 'hstore', OID::Hstore.new
|
145
|
-
m.register_type 'json',
|
90
|
+
m.register_type 'json', Type::Json.new
|
146
91
|
m.register_type 'jsonb', OID::Jsonb.new
|
147
92
|
m.register_type 'cidr', OID::Cidr.new
|
148
93
|
m.register_type 'inet', OID::Inet.new
|
@@ -187,48 +132,29 @@ module ArJdbc
|
|
187
132
|
end
|
188
133
|
end
|
189
134
|
|
190
|
-
load_additional_types
|
191
|
-
|
192
|
-
# pgjdbc returns these if the column is auto-incrmenting
|
193
|
-
m.alias_type 'serial', 'int4'
|
194
|
-
m.alias_type 'bigserial', 'int8'
|
135
|
+
load_additional_types
|
195
136
|
end
|
196
137
|
|
197
|
-
def load_additional_types(
|
198
|
-
initializer =
|
138
|
+
def load_additional_types(oids = nil) # :nodoc:
|
139
|
+
initializer = OID::TypeMapInitializer.new(type_map)
|
199
140
|
|
200
141
|
if supports_ranges?
|
201
142
|
query = <<-SQL
|
202
|
-
SELECT t.oid, t.typname, t.typelem, t.typdelim, t.typinput, r.rngsubtype, t.typtype, t.typbasetype
|
203
|
-
ns.nspname, ns.nspname = ANY(current_schemas(true)) in_ns
|
143
|
+
SELECT t.oid, t.typname, t.typelem, t.typdelim, t.typinput, r.rngsubtype, t.typtype, t.typbasetype
|
204
144
|
FROM pg_type as t
|
205
145
|
LEFT JOIN pg_range as r ON oid = rngtypid
|
206
|
-
JOIN pg_namespace AS ns ON t.typnamespace = ns.oid
|
207
146
|
SQL
|
208
147
|
else
|
209
148
|
query = <<-SQL
|
210
|
-
SELECT t.oid, t.typname, t.typelem, t.typdelim, t.typinput, t.typtype, t.typbasetype
|
211
|
-
ns.nspname, ns.nspname = ANY(current_schemas(true)) in_ns
|
149
|
+
SELECT t.oid, t.typname, t.typelem, t.typdelim, t.typinput, t.typtype, t.typbasetype
|
212
150
|
FROM pg_type as t
|
213
|
-
JOIN pg_namespace AS ns ON t.typnamespace = ns.oid
|
214
151
|
SQL
|
215
152
|
end
|
216
153
|
|
217
|
-
if
|
218
|
-
|
219
|
-
# numeric OID
|
220
|
-
query += "WHERE t.oid::integer = %s" % oid
|
221
|
-
|
222
|
-
elsif m = oid.match(/"?(\w+)"?\."?(\w+)"?/)
|
223
|
-
# namespace and type name
|
224
|
-
query += "WHERE ns.nspname = '%s' AND t.typname = '%s'" % [m[1], m[2]]
|
225
|
-
|
226
|
-
else
|
227
|
-
# only type name
|
228
|
-
query += "WHERE t.typname = '%s' AND ns.nspname = ANY(current_schemas(true))" % oid
|
229
|
-
end
|
154
|
+
if oids
|
155
|
+
query += "WHERE t.oid::integer IN (%s)" % oids.join(", ")
|
230
156
|
else
|
231
|
-
query += initializer.query_conditions_for_initial_load
|
157
|
+
query += initializer.query_conditions_for_initial_load
|
232
158
|
end
|
233
159
|
|
234
160
|
records = execute(query, 'SCHEMA')
|
@@ -247,7 +173,7 @@ module ArJdbc
|
|
247
173
|
ActiveRecord::Type.register(:enum, OID::Enum, adapter: :postgresql)
|
248
174
|
ActiveRecord::Type.register(:hstore, OID::Hstore, adapter: :postgresql)
|
249
175
|
ActiveRecord::Type.register(:inet, OID::Inet, adapter: :postgresql)
|
250
|
-
ActiveRecord::Type.register(:json,
|
176
|
+
ActiveRecord::Type.register(:json, Type::Json, adapter: :postgresql)
|
251
177
|
ActiveRecord::Type.register(:jsonb, OID::Jsonb, adapter: :postgresql)
|
252
178
|
ActiveRecord::Type.register(:money, OID::Money, adapter: :postgresql)
|
253
179
|
ActiveRecord::Type.register(:point, OID::Point, adapter: :postgresql)
|
@@ -12,6 +12,7 @@ require "active_record/connection_adapters/sqlite3/schema_creation"
|
|
12
12
|
require "active_record/connection_adapters/sqlite3/schema_definitions"
|
13
13
|
require "active_record/connection_adapters/sqlite3/schema_dumper"
|
14
14
|
require "active_record/connection_adapters/sqlite3/schema_statements"
|
15
|
+
require "active_support/core_ext/class/attribute"
|
15
16
|
|
16
17
|
module ArJdbc
|
17
18
|
# All the code in this module is a copy of ConnectionAdapters::SQLite3Adapter from active_record 5.
|
@@ -33,11 +34,10 @@ module ArJdbc
|
|
33
34
|
|
34
35
|
# DIFFERENCE: FQN
|
35
36
|
include ::ActiveRecord::ConnectionAdapters::SQLite3::Quoting
|
36
|
-
include ::ActiveRecord::ConnectionAdapters::SQLite3::ColumnDumper
|
37
37
|
include ::ActiveRecord::ConnectionAdapters::SQLite3::SchemaStatements
|
38
38
|
|
39
39
|
NATIVE_DATABASE_TYPES = {
|
40
|
-
primary_key: "
|
40
|
+
primary_key: "integer PRIMARY KEY AUTOINCREMENT NOT NULL",
|
41
41
|
string: { name: "varchar" },
|
42
42
|
text: { name: "text" },
|
43
43
|
integer: { name: "integer" },
|
@@ -47,9 +47,13 @@ module ArJdbc
|
|
47
47
|
time: { name: "time" },
|
48
48
|
date: { name: "date" },
|
49
49
|
binary: { name: "blob" },
|
50
|
-
boolean: { name: "boolean" }
|
50
|
+
boolean: { name: "boolean" },
|
51
|
+
json: { name: "json" },
|
51
52
|
}
|
52
53
|
|
54
|
+
# DIFFERENCE: class_attribute in original adapter is moved down to our section which is a class
|
55
|
+
# since we cannot define it here in the module (original source this is a class).
|
56
|
+
|
53
57
|
class StatementPool < ConnectionAdapters::StatementPool
|
54
58
|
private
|
55
59
|
|
@@ -58,24 +62,11 @@ module ArJdbc
|
|
58
62
|
end
|
59
63
|
end
|
60
64
|
|
61
|
-
|
62
|
-
|
63
|
-
::ActiveRecord::ConnectionAdapters::SQLite3::Table.new(table_name, base)
|
64
|
-
end
|
65
|
-
|
66
|
-
def schema_creation # :nodoc:
|
67
|
-
# DIFFERENCE: FQN
|
68
|
-
::ActiveRecord::ConnectionAdapters::SQLite3::SchemaCreation.new self
|
69
|
-
end
|
70
|
-
|
71
|
-
def arel_visitor # :nodoc:
|
72
|
-
Arel::Visitors::SQLite.new(self)
|
73
|
-
end
|
74
|
-
|
75
|
-
def initialize(connection, logger, connection_options, config)
|
65
|
+
# DIFFERENCE: we remove connection_options because we are not using it.
|
66
|
+
def initialize(connection, logger, config)
|
76
67
|
super(connection, logger, config)
|
77
68
|
|
78
|
-
@active =
|
69
|
+
@active = true
|
79
70
|
@statements = StatementPool.new(self.class.type_cast_config_to_integer(config[:statement_limit]))
|
80
71
|
|
81
72
|
configure_connection
|
@@ -93,12 +84,6 @@ module ArJdbc
|
|
93
84
|
sqlite_version >= "3.8.0"
|
94
85
|
end
|
95
86
|
|
96
|
-
# Returns true, since this connection adapter supports prepared statement
|
97
|
-
# caching.
|
98
|
-
def supports_statement_cache?
|
99
|
-
true
|
100
|
-
end
|
101
|
-
|
102
87
|
def requires_reloading?
|
103
88
|
true
|
104
89
|
end
|
@@ -120,7 +105,7 @@ module ArJdbc
|
|
120
105
|
end
|
121
106
|
|
122
107
|
def active?
|
123
|
-
@active
|
108
|
+
@active
|
124
109
|
end
|
125
110
|
|
126
111
|
# Disconnects from the database if already connected. Otherwise, this
|
@@ -248,53 +233,6 @@ module ArJdbc
|
|
248
233
|
|
249
234
|
# SCHEMA STATEMENTS ========================================
|
250
235
|
|
251
|
-
def new_column_from_field(table_name, field) # :nondoc:
|
252
|
-
case field["dflt_value"]
|
253
|
-
when /^null$/i
|
254
|
-
field["dflt_value"] = nil
|
255
|
-
when /^'(.*)'$/m
|
256
|
-
field["dflt_value"] = $1.gsub("''", "'")
|
257
|
-
when /^"(.*)"$/m
|
258
|
-
field["dflt_value"] = $1.gsub('""', '"')
|
259
|
-
end
|
260
|
-
|
261
|
-
collation = field["collation"]
|
262
|
-
sql_type = field["type"]
|
263
|
-
type_metadata = fetch_type_metadata(sql_type)
|
264
|
-
new_column(field["name"], field["dflt_value"], type_metadata, field["notnull"].to_i == 0, table_name, nil, collation)
|
265
|
-
end
|
266
|
-
|
267
|
-
# Returns an array of indexes for the given table.
|
268
|
-
def indexes(table_name, name = nil) #:nodoc:
|
269
|
-
if name
|
270
|
-
ActiveSupport::Deprecation.warn(<<-MSG.squish)
|
271
|
-
Passing name to #indexes is deprecated without replacement.
|
272
|
-
MSG
|
273
|
-
end
|
274
|
-
|
275
|
-
exec_query("PRAGMA index_list(#{quote_table_name(table_name)})", "SCHEMA").map do |row|
|
276
|
-
sql = <<-SQL
|
277
|
-
SELECT sql
|
278
|
-
FROM sqlite_master
|
279
|
-
WHERE name=#{quote(row['name'])} AND type='index'
|
280
|
-
UNION ALL
|
281
|
-
SELECT sql
|
282
|
-
FROM sqlite_temp_master
|
283
|
-
WHERE name=#{quote(row['name'])} AND type='index'
|
284
|
-
SQL
|
285
|
-
index_sql = exec_query(sql).first["sql"]
|
286
|
-
match = /\sWHERE\s+(.+)$/i.match(index_sql)
|
287
|
-
where = match[1] if match
|
288
|
-
IndexDefinition.new(
|
289
|
-
table_name,
|
290
|
-
row["name"],
|
291
|
-
row["unique"] != 0,
|
292
|
-
exec_query("PRAGMA index_info('#{row['name']}')", "SCHEMA").map { |col|
|
293
|
-
col["name"]
|
294
|
-
}, nil, nil, where)
|
295
|
-
end
|
296
|
-
end
|
297
|
-
|
298
236
|
def primary_keys(table_name) # :nodoc:
|
299
237
|
pks = table_structure(table_name).select { |f| f["pk"] > 0 }
|
300
238
|
pks.sort_by { |f| f["pk"] }.map { |f| f["name"] }
|
@@ -314,19 +252,20 @@ module ArJdbc
|
|
314
252
|
rename_table_indexes(table_name, new_name)
|
315
253
|
end
|
316
254
|
|
317
|
-
#
|
318
|
-
|
319
|
-
|
320
|
-
type
|
255
|
+
# DIFFERENCE: deprecated causes a JRuby 9.1 bug where "super" calls itself -> do inline
|
256
|
+
def valid_alter_table_type?(type, options = {})
|
257
|
+
ActiveSupport::Deprecation.deprecation_warning(__method__)
|
258
|
+
!invalid_alter_table_type?(type, options)
|
321
259
|
end
|
260
|
+
#deprecate :valid_alter_table_type?
|
322
261
|
|
323
262
|
def add_column(table_name, column_name, type, options = {}) #:nodoc:
|
324
|
-
if
|
325
|
-
super(table_name, column_name, type, options)
|
326
|
-
else
|
263
|
+
if invalid_alter_table_type?(type, options)
|
327
264
|
alter_table(table_name) do |definition|
|
328
265
|
definition.column(column_name, type, options)
|
329
266
|
end
|
267
|
+
else
|
268
|
+
super
|
330
269
|
end
|
331
270
|
end
|
332
271
|
|
@@ -391,8 +330,32 @@ module ArJdbc
|
|
391
330
|
::ActiveRecord::ConnectionAdapters::ForeignKeyDefinition.new(table_name, row["table"], options)
|
392
331
|
end
|
393
332
|
end
|
333
|
+
|
334
|
+
def insert_fixtures(rows, table_name)
|
335
|
+
ActiveSupport::Deprecation.warn(<<-MSG.squish)
|
336
|
+
`insert_fixtures` is deprecated and will be removed in the next version of Rails.
|
337
|
+
Consider using `insert_fixtures_set` for performance improvement.
|
338
|
+
MSG
|
339
|
+
insert_fixtures_set(table_name => rows)
|
340
|
+
end
|
341
|
+
|
342
|
+
def insert_fixtures_set(fixture_set, tables_to_delete = [])
|
343
|
+
disable_referential_integrity do
|
344
|
+
transaction(requires_new: true) do
|
345
|
+
tables_to_delete.each { |table| delete "DELETE FROM #{quote_table_name(table)}", "Fixture Delete" }
|
346
|
+
|
347
|
+
fixture_set.each do |table_name, rows|
|
348
|
+
rows.each { |row| insert_fixture(row, table_name) }
|
349
|
+
end
|
350
|
+
end
|
351
|
+
end
|
352
|
+
end
|
394
353
|
|
395
354
|
private
|
355
|
+
def initialize_type_map(m = type_map)
|
356
|
+
super
|
357
|
+
register_class_with_limit m, %r(int)i, SQLite3Integer
|
358
|
+
end
|
396
359
|
|
397
360
|
def table_structure(table_name)
|
398
361
|
structure = exec_query("PRAGMA table_info(#{quote_table_name(table_name)})", "SCHEMA")
|
@@ -400,7 +363,13 @@ module ArJdbc
|
|
400
363
|
table_structure_with_collation(table_name, structure)
|
401
364
|
end
|
402
365
|
alias column_definitions table_structure
|
403
|
-
|
366
|
+
|
367
|
+
# See: https://www.sqlite.org/lang_altertable.html
|
368
|
+
# SQLite has an additional restriction on the ALTER TABLE statement
|
369
|
+
def invalid_alter_table_type?(type, options)
|
370
|
+
type.to_sym == :primary_key || options[:primary_key]
|
371
|
+
end
|
372
|
+
|
404
373
|
def alter_table(table_name, options = {}) #:nodoc:
|
405
374
|
altered_table_name = "a#{table_name}"
|
406
375
|
caller = lambda { |definition| yield definition if block_given? }
|
@@ -551,23 +520,28 @@ module ArJdbc
|
|
551
520
|
end
|
552
521
|
end
|
553
522
|
|
554
|
-
def
|
555
|
-
|
556
|
-
::ActiveRecord::ConnectionAdapters::SQLite3::TableDefinition.new(*args)
|
557
|
-
end
|
558
|
-
|
559
|
-
def extract_foreign_key_action(specifier)
|
560
|
-
case specifier
|
561
|
-
when "CASCADE"; :cascade
|
562
|
-
when "SET NULL"; :nullify
|
563
|
-
when "RESTRICT"; :restrict
|
564
|
-
end
|
523
|
+
def arel_visitor
|
524
|
+
Arel::Visitors::SQLite.new(self)
|
565
525
|
end
|
566
526
|
|
567
527
|
def configure_connection
|
568
528
|
execute("PRAGMA foreign_keys = ON", "SCHEMA")
|
569
529
|
end
|
530
|
+
|
531
|
+
# DIFFERENCE: FQN
|
532
|
+
class SQLite3Integer < ::ActiveRecord::Type::Integer # :nodoc:
|
533
|
+
private
|
534
|
+
def _limit
|
535
|
+
# INTEGER storage class can be stored 8 bytes value.
|
536
|
+
# See https://www.sqlite.org/datatype3.html#storage_classes_and_datatypes
|
537
|
+
limit || 8
|
538
|
+
end
|
539
|
+
end
|
540
|
+
|
541
|
+
# DIFFERENCE: FQN
|
542
|
+
::ActiveRecord::Type.register(:integer, SQLite3Integer, adapter: :sqlite3)
|
570
543
|
end
|
544
|
+
# DIFFERENCE: A registration here is moved down to concrete class so we are not registering part of an adapter.
|
571
545
|
end
|
572
546
|
|
573
547
|
module ActiveRecord::ConnectionAdapters
|
@@ -677,6 +651,25 @@ module ActiveRecord::ConnectionAdapters
|
|
677
651
|
include ArJdbc::Abstract::StatementCache
|
678
652
|
include ArJdbc::Abstract::TransactionSupport
|
679
653
|
|
654
|
+
# Note: This is part of original AR sqlite3_adapter.rb and not an override by us. This is to just
|
655
|
+
# work around our copy of Sqlite3Adapter being a module above and not a class.
|
656
|
+
##
|
657
|
+
# :singleton-method:
|
658
|
+
# Indicates whether boolean values are stored in sqlite3 databases as 1
|
659
|
+
# and 0 or 't' and 'f'. Leaving <tt>ActiveRecord::ConnectionAdapters::SQLite3Adapter.represent_boolean_as_integer</tt>
|
660
|
+
# set to false is deprecated. SQLite databases have used 't' and 'f' to
|
661
|
+
# serialize boolean values and must have old data converted to 1 and 0
|
662
|
+
# (its native boolean serialization) before setting this flag to true.
|
663
|
+
# Conversion can be accomplished by setting up a rake task which runs
|
664
|
+
#
|
665
|
+
# ExampleModel.where("boolean_column = 't'").update_all(boolean_column: 1)
|
666
|
+
# ExampleModel.where("boolean_column = 'f'").update_all(boolean_column: 0)
|
667
|
+
# for all models and all boolean columns, after which the flag must be set
|
668
|
+
# to true by adding the following to your <tt>application.rb</tt> file:
|
669
|
+
#
|
670
|
+
# Rails.application.config.active_record.sqlite3.represent_boolean_as_integer = true
|
671
|
+
class_attribute :represent_boolean_as_integer, default: false
|
672
|
+
|
680
673
|
def supports_transaction_isolation?
|
681
674
|
false
|
682
675
|
end
|
@@ -704,5 +697,8 @@ module ActiveRecord::ConnectionAdapters
|
|
704
697
|
def self.jdbc_connection_class
|
705
698
|
::ActiveRecord::ConnectionAdapters::SQLite3JdbcConnection
|
706
699
|
end
|
700
|
+
|
701
|
+
# Note: This is not an override of ours but a moved line from AR Sqlite3Adapter to register ours vs our copied module (which would be their class).
|
702
|
+
# ActiveSupport.run_load_hooks(:active_record_sqlite3adapter, SQLite3Adapter)
|
707
703
|
end
|
708
704
|
end
|