activerecord-oracle_enhanced-adapter 6.0.6 → 6.1.0.rc1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/History.md +80 -4
- data/README.md +1 -1
- data/VERSION +1 -1
- data/lib/active_record/connection_adapters/oracle_enhanced/connection.rb +2 -3
- data/lib/active_record/connection_adapters/oracle_enhanced/context_index.rb +0 -1
- data/lib/active_record/connection_adapters/oracle_enhanced/database_limits.rb +0 -9
- data/lib/active_record/connection_adapters/oracle_enhanced/database_statements.rb +7 -9
- data/lib/active_record/connection_adapters/oracle_enhanced/database_tasks.rb +4 -5
- data/lib/active_record/connection_adapters/oracle_enhanced/dbms_output.rb +0 -1
- data/lib/active_record/connection_adapters/oracle_enhanced/jdbc_connection.rb +3 -4
- data/lib/active_record/connection_adapters/oracle_enhanced/lob.rb +1 -2
- data/lib/active_record/connection_adapters/oracle_enhanced/oci_connection.rb +2 -3
- data/lib/active_record/connection_adapters/oracle_enhanced/procedures.rb +0 -1
- data/lib/active_record/connection_adapters/oracle_enhanced/quoting.rb +2 -3
- data/lib/active_record/connection_adapters/oracle_enhanced/schema_creation.rb +2 -3
- data/lib/active_record/connection_adapters/oracle_enhanced/schema_dumper.rb +16 -4
- data/lib/active_record/connection_adapters/oracle_enhanced/schema_statements.rb +55 -55
- data/lib/active_record/connection_adapters/oracle_enhanced/structure_dump.rb +35 -39
- data/lib/active_record/connection_adapters/oracle_enhanced/type_metadata.rb +2 -1
- data/lib/active_record/connection_adapters/oracle_enhanced_adapter.rb +58 -40
- data/lib/active_record/type/oracle_enhanced/boolean.rb +0 -1
- data/lib/active_record/type/oracle_enhanced/integer.rb +0 -1
- data/lib/arel/visitors/oracle.rb +253 -0
- data/lib/arel/visitors/oracle12.rb +160 -0
- data/spec/active_record/connection_adapters/oracle_enhanced/connection_spec.rb +9 -3
- data/spec/active_record/connection_adapters/oracle_enhanced/database_tasks_spec.rb +6 -1
- data/spec/active_record/connection_adapters/oracle_enhanced/procedures_spec.rb +0 -1
- data/spec/active_record/connection_adapters/oracle_enhanced/schema_dumper_spec.rb +27 -0
- data/spec/active_record/connection_adapters/oracle_enhanced/structure_dump_spec.rb +2 -2
- data/spec/active_record/connection_adapters/oracle_enhanced_adapter_spec.rb +30 -60
- data/spec/active_record/oracle_enhanced/type/national_character_string_spec.rb +4 -2
- data/spec/spec_config.yaml.template +2 -2
- data/spec/spec_helper.rb +13 -2
- data/spec/support/stats.sql +3 -0
- metadata +31 -27
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 47264bf6ac81ec4786fb1c3021c29661b8a02df12ac7a2ffc2e4ad02353794dd
|
4
|
+
data.tar.gz: eaceb8f2950700b0cc5eba5c1b0f7dae657bf26aa529444e83d901c7a4cb46ac
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0c96bb5cdf7508d310484f6a6f25bec23c9eee8029df4e9cd4075f6acd1671c02d90837db4a88ca054745d218664049b55ec238cb5313d47dbbf868b85d829ea
|
7
|
+
data.tar.gz: 2ef70ebd9e11f9c6a5739b7644c4ac770b4fb2c3ebc2b56b46479625b3de0f89d78f77618ac7fe077416a373859662d5c4dd11ee7ff0eca4651198aca181d973
|
data/History.md
CHANGED
@@ -1,9 +1,85 @@
|
|
1
|
-
## 6.0.
|
1
|
+
## 6.1.0.rc1 / 2020-11-03
|
2
2
|
|
3
3
|
* Changes and bug fixes
|
4
|
-
*
|
5
|
-
* Add
|
6
|
-
* `
|
4
|
+
* Support Rails 6.1.0.rc1
|
5
|
+
* Add support to change the permissions granted when creating DB [#1885]
|
6
|
+
* Refactor `create_table`'s options separation [#1886]
|
7
|
+
* Move schema cache to pool [#1888]
|
8
|
+
* Clear schema cache when a table is created/dropped/renamed [#1891]
|
9
|
+
* Deduplicate various Active Record schema cache structures [#1897]
|
10
|
+
* Support SQLCounter change to ignore "SCHEMA" and "TRANSACTION" log [#1892]
|
11
|
+
* Share the column and table name quote cache between connections [#1901]
|
12
|
+
* Add database_exists? method to connection adapters [#1906]
|
13
|
+
* Accept columns passed with options in remove_index [#1930]
|
14
|
+
* Fix `NameError` for `SchemaCreation` [#1933]
|
15
|
+
* Add `supports_common_table_expressions?` for CTE testing [#1946]
|
16
|
+
* create_table_definition and add_column take keyword arguments [#1942]
|
17
|
+
* Address `uninitialized constant ActiveRecord::ConnectionAdapters::AbstractAdapter::Quoting (NameError) [#1950]
|
18
|
+
* Fix an error when writing lobs [#1962]
|
19
|
+
* Uninstall SimpleCov [#1968]
|
20
|
+
* fix: Auto retry only works for connection.exec() [#1976]
|
21
|
+
* Fix keyword arguments errors for Ruby 2.8.0-dev [#1977]
|
22
|
+
* Fix a build errors when using Ruby 2.8.0-dev [#1983]
|
23
|
+
* Include sync option when dumping a context index [#1988]
|
24
|
+
* Use `build_result` instead of `ActiveRecord::Result.new` [#1994]
|
25
|
+
* Use the new API for build_results [#1995]
|
26
|
+
* Merge Arel visitors [#2002]
|
27
|
+
* Enable `Rails/IndexBy` and `Rails/IndexWith` cops [#2006]
|
28
|
+
* Don't refer `allowed_index_name_length` directly [#2009]
|
29
|
+
* Should not rely on the global `Arel::Table.engine` in the framework [#2010]
|
30
|
+
* Suppress `warning: already initialized constant` [#2011]
|
31
|
+
* Deprecate passing a column to `type_cast` [#2012]
|
32
|
+
* Limit number of expressions in a list during a "homogenous in" operation [#2013]
|
33
|
+
* Allow column name with function (e.g. `length(title)`) as safe SQL string [#2017]
|
34
|
+
* Default engine `ENGINE=InnoDB` is no longer dumped to make schema more agnostic [#2019]
|
35
|
+
* Separate primary key column options from table options [#2019]
|
36
|
+
* Make index options to kwargs [#2022]
|
37
|
+
* Make remaining migration options to kwargs [#2024]
|
38
|
+
* Allow TruffleRuby RUBY_ENGINE [#2046]
|
39
|
+
* Restore Schema Dumper behavior changed by #2019 [#2047]
|
40
|
+
* Support JDBC service name syntax [#2035]
|
41
|
+
* Use Rake 13.0.0.pre.1 [#1924]
|
42
|
+
* Bump RuboCop version to 0.71 [#1887]
|
43
|
+
* Bump RuboCop to 0.74.0 [#1914]
|
44
|
+
* Bump RuboCop to 0.76.0 [#1947]
|
45
|
+
* Use RuboCop 0.77 [#1959]
|
46
|
+
* Bump RuboCop to 0.82.0 [#2005]
|
47
|
+
* Suppress RuboCop's offenses [#2020]
|
48
|
+
* Enable `Layout/EmptyLinesAroundAccessModifier` cop [#1890]
|
49
|
+
* Disable `Style/BracesAroundHashParameters` cop [#1923]
|
50
|
+
* Enable `Layout/ClosingHeredocIndentation` cop [#1958]
|
51
|
+
* Unlock RuboCop gem versions [#1926]
|
52
|
+
* Enable `Rails/IndexBy` and `Rails/IndexWith` cops [#2006]
|
53
|
+
* Enable `Performance/DeletePrefix` and `Performance/DeleteSuffix` cops [#2021]
|
54
|
+
* Enable `Layout/SpaceAroundOperators` cop [#2057]
|
55
|
+
* Fix links to rails-dev-box running on docker [#1883]
|
56
|
+
* Fix spec config template copy instructions [#1884]
|
57
|
+
* Update UPGRADE section for Rails 5.2 [#1993]
|
58
|
+
|
59
|
+
* CI
|
60
|
+
* Enable GitHub Actions and run RuboCop [#1925]
|
61
|
+
* Run CI with GitHub Actions [#2015]
|
62
|
+
* Enabled Dependabot by creating .dependabot/config.yml [#1931]
|
63
|
+
* Disable Code Climate #1938
|
64
|
+
* CI against JRuby 9.2.8.0 [#1911]
|
65
|
+
* CI against JRuby 9.2.9.0 #1948
|
66
|
+
* CI against Ruby 2.6.4 and Ruby 2.5.6 [#1921]
|
67
|
+
* CI against Ruby 2.5.7 and Ruby 2.6.5 [#1949]
|
68
|
+
* CI against Ruby 2.7.0 [#1975]
|
69
|
+
* CI against JRuby 9.2.10.0 [#1989]
|
70
|
+
* CI against JRuby 9.2.11.0 [#1992]
|
71
|
+
* CI against JRuby 9.2.11.1 [#1997]
|
72
|
+
* CI againt Ruby 2.7.1, 2.6.6 and 2.5.8 #1998
|
73
|
+
* CI against JRuby 9.2.12.0 [#2034]
|
74
|
+
* Use Oracle Instant Client 18.5 [#2036]
|
75
|
+
* Support `jruby-head` again [#2037]
|
76
|
+
* CI against JRuby 9.2.13.0 [#2041]
|
77
|
+
* CI against Ruby 2.7.2 [#2052]
|
78
|
+
* Remove unnecessary PATH and LD_LIBRARY_PATH environment variables [#1927]
|
79
|
+
* Use Ubuntu 18.04 (Bionic Beaver) at Travis CI [#1937]
|
80
|
+
* Run bug report template at CI [#1936]
|
81
|
+
* Skip known failures until #1943 is resolved [#1961]
|
82
|
+
* Migrate to `ruby/setup-ruby` to use Ruby 2.7 [#2026]
|
7
83
|
|
8
84
|
## 6.0.4 / 2020-08-18
|
9
85
|
|
data/README.md
CHANGED
@@ -663,7 +663,7 @@ if any database structure changed by migrations, execute `rails db:schema:cache:
|
|
663
663
|
|
664
664
|
UPGRADE
|
665
665
|
---------------
|
666
|
-
### Upgrade Rails 5.
|
666
|
+
### Upgrade Rails 5.1 or older version to Rails 5.2
|
667
667
|
|
668
668
|
* `emulate_booleans_from_strings = true` change
|
669
669
|
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
6.0.
|
1
|
+
6.1.0.rc1
|
@@ -19,7 +19,6 @@ module ActiveRecord
|
|
19
19
|
attr_reader :raw_connection
|
20
20
|
|
21
21
|
private
|
22
|
-
|
23
22
|
# Used always by JDBC connection as well by OCI connection when describing tables over database link
|
24
23
|
def describe(name)
|
25
24
|
name = name.to_s
|
@@ -116,8 +115,8 @@ module ActiveRecord
|
|
116
115
|
end
|
117
116
|
end
|
118
117
|
|
119
|
-
# if MRI or YARV
|
120
|
-
if !defined?(RUBY_ENGINE) || RUBY_ENGINE == "ruby"
|
118
|
+
# if MRI or YARV or TruffleRuby
|
119
|
+
if !defined?(RUBY_ENGINE) || RUBY_ENGINE == "ruby" || RUBY_ENGINE == "truffleruby"
|
121
120
|
ORACLE_ENHANCED_CONNECTION = :oci
|
122
121
|
require "active_record/connection_adapters/oracle_enhanced/oci_connection"
|
123
122
|
# if JRuby
|
@@ -142,7 +142,6 @@ module ActiveRecord
|
|
142
142
|
end
|
143
143
|
|
144
144
|
private
|
145
|
-
|
146
145
|
def create_datastore_procedure(table_name, procedure_name, column_names, options)
|
147
146
|
quoted_table_name = quote_table_name(table_name)
|
148
147
|
select_queries, column_names = column_names.partition { |c| c.to_s =~ /^\s*SELECT\s+/i }
|
@@ -25,15 +25,6 @@ module ActiveRecord
|
|
25
25
|
end
|
26
26
|
deprecate :column_name_length
|
27
27
|
|
28
|
-
# Returns the maximum allowed length for an index name. This
|
29
|
-
# limit is enforced by rails and Is less than or equal to
|
30
|
-
# <tt>index_name_length</tt>. The gap between
|
31
|
-
# <tt>index_name_length</tt> is to allow internal rails
|
32
|
-
# opreations to use prefixes in temporary opreations.
|
33
|
-
def allowed_index_name_length
|
34
|
-
index_name_length
|
35
|
-
end
|
36
|
-
|
37
28
|
# the maximum length of an index name
|
38
29
|
# supported by this database
|
39
30
|
def index_name_length
|
@@ -42,7 +42,7 @@ module ActiveRecord
|
|
42
42
|
cursor.exec
|
43
43
|
end
|
44
44
|
|
45
|
-
if (name == "EXPLAIN") && sql
|
45
|
+
if (name == "EXPLAIN") && sql.start_with?("EXPLAIN")
|
46
46
|
res = true
|
47
47
|
else
|
48
48
|
columns = cursor.get_col_names.map do |col_name|
|
@@ -53,7 +53,7 @@ module ActiveRecord
|
|
53
53
|
while row = cursor.fetch(fetch_options)
|
54
54
|
rows << row
|
55
55
|
end
|
56
|
-
res =
|
56
|
+
res = build_result(columns: columns, rows: rows)
|
57
57
|
end
|
58
58
|
|
59
59
|
cursor.close unless cached
|
@@ -67,7 +67,7 @@ module ActiveRecord
|
|
67
67
|
|
68
68
|
def explain(arel, binds = [])
|
69
69
|
sql = "EXPLAIN PLAN FOR #{to_sql(arel, binds)}"
|
70
|
-
return if
|
70
|
+
return if /FROM all_/.match?(sql)
|
71
71
|
if ORACLE_ENHANCED_CONNECTION == :jdbc
|
72
72
|
exec_query(sql, "EXPLAIN", binds)
|
73
73
|
else
|
@@ -130,7 +130,7 @@ module ActiveRecord
|
|
130
130
|
rows << [returning_id]
|
131
131
|
end
|
132
132
|
cursor.close unless cached
|
133
|
-
|
133
|
+
build_result(columns: returning_id_col || [], rows: rows)
|
134
134
|
end
|
135
135
|
end
|
136
136
|
|
@@ -196,11 +196,11 @@ module ActiveRecord
|
|
196
196
|
end
|
197
197
|
|
198
198
|
def create_savepoint(name = current_savepoint_name) #:nodoc:
|
199
|
-
execute("SAVEPOINT #{name}")
|
199
|
+
execute("SAVEPOINT #{name}", "TRANSACTION")
|
200
200
|
end
|
201
201
|
|
202
202
|
def exec_rollback_to_savepoint(name = current_savepoint_name) #:nodoc:
|
203
|
-
execute("ROLLBACK TO #{name}")
|
203
|
+
execute("ROLLBACK TO #{name}", "TRANSACTION")
|
204
204
|
end
|
205
205
|
|
206
206
|
def release_savepoint(name = current_savepoint_name) #:nodoc:
|
@@ -254,11 +254,9 @@ module ActiveRecord
|
|
254
254
|
columns.each do |col|
|
255
255
|
value = attributes[col.name]
|
256
256
|
# changed sequence of next two lines - should check if value is nil before converting to yaml
|
257
|
-
next
|
257
|
+
next if value.blank?
|
258
258
|
if klass.attribute_types[col.name].is_a? Type::Serialized
|
259
259
|
value = klass.attribute_types[col.name].serialize(value)
|
260
|
-
# value can be nil after serialization because ActiveRecord serializes [] and {} as nil
|
261
|
-
next unless value
|
262
260
|
end
|
263
261
|
uncached do
|
264
262
|
unless lob_record = select_one(sql = <<~SQL.squish, "Writable Large Object")
|
@@ -27,11 +27,10 @@ module ActiveRecord
|
|
27
27
|
raise e
|
28
28
|
end
|
29
29
|
end
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
connection.execute "GRANT create sequence TO #{@config['username']}"
|
30
|
+
|
31
|
+
OracleEnhancedAdapter.permissions.each do |permission|
|
32
|
+
connection.execute "GRANT #{permission} TO #{@config['username']}"
|
33
|
+
end
|
35
34
|
end
|
36
35
|
|
37
36
|
def drop
|
@@ -115,9 +115,9 @@ module ActiveRecord
|
|
115
115
|
else
|
116
116
|
unless database.match?(/^(\:|\/)/)
|
117
117
|
# assume database is a SID if no colon or slash are supplied (backward-compatibility)
|
118
|
-
database = "
|
118
|
+
database = "/#{database}"
|
119
119
|
end
|
120
|
-
url = config[:url] || "jdbc:oracle:thin
|
120
|
+
url = config[:url] || "jdbc:oracle:thin:@//#{host || 'localhost'}:#{port || 1521}#{database}"
|
121
121
|
end
|
122
122
|
|
123
123
|
prefetch_rows = config[:prefetch_rows] || 100
|
@@ -238,7 +238,7 @@ module ActiveRecord
|
|
238
238
|
begin
|
239
239
|
yield if block_given?
|
240
240
|
rescue Java::JavaSql::SQLException => e
|
241
|
-
raise unless
|
241
|
+
raise unless /^(Closed Connection|Io exception:|No more data to read from socket|IO Error:)/.match?(e.message)
|
242
242
|
@active = false
|
243
243
|
raise unless should_retry
|
244
244
|
should_retry = false
|
@@ -512,7 +512,6 @@ module ActiveRecord
|
|
512
512
|
end
|
513
513
|
|
514
514
|
private
|
515
|
-
|
516
515
|
def lob_to_ruby_value(val)
|
517
516
|
case val
|
518
517
|
when ::Java::OracleSql::CLOB
|
@@ -18,13 +18,12 @@ module ActiveRecord #:nodoc:
|
|
18
18
|
module ClassMethods
|
19
19
|
def lob_columns
|
20
20
|
columns.select do |column|
|
21
|
-
column.sql_type_metadata.sql_type
|
21
|
+
column.sql_type_metadata.sql_type.end_with?("LOB")
|
22
22
|
end
|
23
23
|
end
|
24
24
|
end
|
25
25
|
|
26
26
|
private
|
27
|
-
|
28
27
|
def enhanced_write_lobs
|
29
28
|
if self.class.connection.is_a?(ConnectionAdapters::OracleEnhancedAdapter) &&
|
30
29
|
!(self.class.custom_create_method || self.class.custom_update_method)
|
@@ -269,7 +269,6 @@ module ActiveRecord
|
|
269
269
|
end
|
270
270
|
|
271
271
|
private
|
272
|
-
|
273
272
|
def date_without_time?(value)
|
274
273
|
case value
|
275
274
|
when OraDate
|
@@ -323,9 +322,9 @@ module ActiveRecord
|
|
323
322
|
# connection using host, port and database name
|
324
323
|
elsif host || port
|
325
324
|
host ||= "localhost"
|
326
|
-
host = "[#{host}]" if
|
325
|
+
host = "[#{host}]" if /^[^\[].*:/.match?(host) # IPv6
|
327
326
|
port ||= 1521
|
328
|
-
database = "/#{database}" unless database.
|
327
|
+
database = "/#{database}" unless database.start_with?("/")
|
329
328
|
"//#{host}:#{port}#{database}"
|
330
329
|
# if no host is specified then assume that
|
331
330
|
# database parameter is TNS alias or TNS connection string
|
@@ -169,7 +169,6 @@ module ActiveRecord
|
|
169
169
|
private_constant :COLUMN_NAME, :COLUMN_NAME_WITH_ORDER
|
170
170
|
|
171
171
|
private
|
172
|
-
|
173
172
|
def oracle_downcase(column_name)
|
174
173
|
return nil if column_name.nil?
|
175
174
|
/[a-z]/.match?(column_name) ? column_name : column_name.downcase
|
@@ -179,8 +178,8 @@ module ActiveRecord
|
|
179
178
|
end
|
180
179
|
end
|
181
180
|
|
182
|
-
# if MRI or YARV
|
183
|
-
if !defined?(RUBY_ENGINE) || RUBY_ENGINE == "ruby"
|
181
|
+
# if MRI or YARV or TruffleRuby
|
182
|
+
if !defined?(RUBY_ENGINE) || RUBY_ENGINE == "ruby" || RUBY_ENGINE == "truffleruby"
|
184
183
|
require "active_record/connection_adapters/oracle_enhanced/oci_quoting"
|
185
184
|
# if JRuby
|
186
185
|
elsif RUBY_ENGINE == "jruby"
|
@@ -3,9 +3,8 @@
|
|
3
3
|
module ActiveRecord
|
4
4
|
module ConnectionAdapters
|
5
5
|
module OracleEnhanced
|
6
|
-
class SchemaCreation <
|
6
|
+
class SchemaCreation < SchemaCreation
|
7
7
|
private
|
8
|
-
|
9
8
|
def visit_ColumnDefinition(o)
|
10
9
|
if [:blob, :clob, :nclob].include?(sql_type = type_to_sql(o.type, **o.options).downcase.to_sym)
|
11
10
|
if (tablespace = default_tablespace_for(sql_type))
|
@@ -36,7 +35,7 @@ module ActiveRecord
|
|
36
35
|
create_sql << " TABLESPACE #{tablespace}"
|
37
36
|
end
|
38
37
|
end
|
39
|
-
add_table_options!(create_sql,
|
38
|
+
add_table_options!(create_sql, o)
|
40
39
|
create_sql << " AS #{to_sql(o.as)}" if o.as
|
41
40
|
create_sql
|
42
41
|
end
|
@@ -4,7 +4,15 @@ module ActiveRecord #:nodoc:
|
|
4
4
|
module ConnectionAdapters #:nodoc:
|
5
5
|
module OracleEnhanced #:nodoc:
|
6
6
|
class SchemaDumper < ConnectionAdapters::SchemaDumper #:nodoc:
|
7
|
+
DEFAULT_PRIMARY_KEY_COLUMN_SPEC = { precision: "38", null: "false" }.freeze
|
8
|
+
private_constant :DEFAULT_PRIMARY_KEY_COLUMN_SPEC
|
9
|
+
|
7
10
|
private
|
11
|
+
def column_spec_for_primary_key(column)
|
12
|
+
spec = super
|
13
|
+
spec.except!(:precision) if prepare_column_options(column) == DEFAULT_PRIMARY_KEY_COLUMN_SPEC
|
14
|
+
spec
|
15
|
+
end
|
8
16
|
|
9
17
|
def tables(stream)
|
10
18
|
# do not include materialized views in schema dump - they should be created separately after schema creation
|
@@ -51,6 +59,7 @@ module ActiveRecord #:nodoc:
|
|
51
59
|
else
|
52
60
|
statement_parts = [ ("add_context_index " + remove_prefix_and_suffix(table).inspect) ]
|
53
61
|
statement_parts << index.columns.inspect
|
62
|
+
statement_parts << ("sync: " + $1.inspect) if index.parameters =~ /SYNC\((.*?)\)/
|
54
63
|
statement_parts << ("name: " + index.name.inspect)
|
55
64
|
end
|
56
65
|
else
|
@@ -72,7 +81,7 @@ module ActiveRecord #:nodoc:
|
|
72
81
|
index_statements = indexes.map do |index|
|
73
82
|
" t.index #{index_parts(index).join(', ')}" unless index.type == "CTXSYS.CONTEXT"
|
74
83
|
end
|
75
|
-
stream.puts index_statements.sort.join("\n")
|
84
|
+
stream.puts index_statements.compact.sort.join("\n")
|
76
85
|
end
|
77
86
|
end
|
78
87
|
|
@@ -107,7 +116,10 @@ module ActiveRecord #:nodoc:
|
|
107
116
|
tbl.print ", primary_key: #{pk.inspect}" unless pk == "id"
|
108
117
|
pkcol = columns.detect { |c| c.name == pk }
|
109
118
|
pkcolspec = column_spec_for_primary_key(pkcol)
|
110
|
-
|
119
|
+
unless pkcolspec.empty?
|
120
|
+
if pkcolspec != pkcolspec.slice(:id, :default)
|
121
|
+
pkcolspec = { id: { type: pkcolspec.delete(:id), **pkcolspec }.compact }
|
122
|
+
end
|
111
123
|
tbl.print ", #{format_colspec(pkcolspec)}"
|
112
124
|
end
|
113
125
|
when Array
|
@@ -168,8 +180,8 @@ module ActiveRecord #:nodoc:
|
|
168
180
|
|
169
181
|
def extract_expression_for_virtual_column(column)
|
170
182
|
column_name = column.name
|
171
|
-
@connection.select_value(<<~SQL.squish, "
|
172
|
-
select
|
183
|
+
@connection.select_value(<<~SQL.squish, "SCHEMA", [bind_string("table_name", table_name.upcase), bind_string("column_name", column_name.upcase)]).inspect
|
184
|
+
select data_default from all_tab_columns
|
173
185
|
where owner = SYS_CONTEXT('userenv', 'current_schema')
|
174
186
|
and table_name = :table_name
|
175
187
|
and column_name = :column_name
|
@@ -11,9 +11,8 @@ module ActiveRecord
|
|
11
11
|
# see: abstract/schema_statements.rb
|
12
12
|
|
13
13
|
def tables #:nodoc:
|
14
|
-
select_values(<<~SQL.squish, "
|
15
|
-
SELECT
|
16
|
-
DECODE(table_name, UPPER(table_name), LOWER(table_name), table_name)
|
14
|
+
select_values(<<~SQL.squish, "SCHEMA")
|
15
|
+
SELECT DECODE(table_name, UPPER(table_name), LOWER(table_name), table_name)
|
17
16
|
FROM all_tables
|
18
17
|
WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
19
18
|
AND secondary = 'N'
|
@@ -44,8 +43,8 @@ module ActiveRecord
|
|
44
43
|
table_owner, table_name = default_owner, real_name
|
45
44
|
end
|
46
45
|
|
47
|
-
select_values(<<~SQL.squish, "
|
48
|
-
SELECT
|
46
|
+
select_values(<<~SQL.squish, "SCHEMA", [bind_string("owner", table_owner), bind_string("table_name", table_name)]).any?
|
47
|
+
SELECT owner, table_name
|
49
48
|
FROM all_tables
|
50
49
|
WHERE owner = :owner
|
51
50
|
AND table_name = :table_name
|
@@ -60,22 +59,20 @@ module ActiveRecord
|
|
60
59
|
end
|
61
60
|
|
62
61
|
def views # :nodoc:
|
63
|
-
select_values(<<~SQL.squish, "
|
64
|
-
SELECT
|
65
|
-
LOWER(view_name) FROM all_views WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
62
|
+
select_values(<<~SQL.squish, "SCHEMA")
|
63
|
+
SELECT LOWER(view_name) FROM all_views WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
66
64
|
SQL
|
67
65
|
end
|
68
66
|
|
69
67
|
def materialized_views #:nodoc:
|
70
|
-
select_values(<<~SQL.squish, "
|
71
|
-
SELECT
|
72
|
-
LOWER(mview_name) FROM all_mviews WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
68
|
+
select_values(<<~SQL.squish, "SCHEMA")
|
69
|
+
SELECT LOWER(mview_name) FROM all_mviews WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
73
70
|
SQL
|
74
71
|
end
|
75
72
|
|
76
73
|
# get synonyms for schema dump
|
77
74
|
def synonyms
|
78
|
-
result = select_all(<<~SQL.squish, "
|
75
|
+
result = select_all(<<~SQL.squish, "SCHEMA")
|
79
76
|
SELECT synonym_name, table_owner, table_name
|
80
77
|
FROM all_synonyms where owner = SYS_CONTEXT('userenv', 'current_schema')
|
81
78
|
SQL
|
@@ -90,8 +87,8 @@ module ActiveRecord
|
|
90
87
|
(_owner, table_name) = @connection.describe(table_name)
|
91
88
|
default_tablespace_name = default_tablespace
|
92
89
|
|
93
|
-
result = select_all(<<~SQL.squish, "
|
94
|
-
SELECT
|
90
|
+
result = select_all(<<~SQL.squish, "SCHEMA", [bind_string("table_name", table_name)])
|
91
|
+
SELECT LOWER(i.table_name) AS table_name, LOWER(i.index_name) AS index_name, i.uniqueness,
|
95
92
|
i.index_type, i.ityp_owner, i.ityp_name, i.parameters,
|
96
93
|
LOWER(i.tablespace_name) AS tablespace_name,
|
97
94
|
LOWER(c.column_name) AS column_name, e.column_expression,
|
@@ -120,8 +117,8 @@ module ActiveRecord
|
|
120
117
|
statement_parameters = nil
|
121
118
|
if row["index_type"] == "DOMAIN" && row["ityp_owner"] == "CTXSYS" && row["ityp_name"] == "CONTEXT"
|
122
119
|
procedure_name = default_datastore_procedure(row["index_name"])
|
123
|
-
source = select_values(<<~SQL.squish, "
|
124
|
-
SELECT
|
120
|
+
source = select_values(<<~SQL.squish, "SCHEMA", [bind_string("procedure_name", procedure_name.upcase)]).join
|
121
|
+
SELECT text
|
125
122
|
FROM all_source
|
126
123
|
WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
127
124
|
AND name = :procedure_name
|
@@ -199,19 +196,19 @@ module ActiveRecord
|
|
199
196
|
# t.string :last_name, :comment => “Surname”
|
200
197
|
# end
|
201
198
|
|
202
|
-
def create_table(table_name, **options)
|
203
|
-
create_sequence =
|
204
|
-
td = create_table_definition
|
199
|
+
def create_table(table_name, id: :primary_key, primary_key: nil, force: nil, **options)
|
200
|
+
create_sequence = id != false
|
201
|
+
td = create_table_definition(
|
202
|
+
table_name, **options.extract!(:temporary, :options, :as, :comment, :tablespace, :organization)
|
203
|
+
)
|
205
204
|
|
206
|
-
if
|
207
|
-
pk =
|
208
|
-
Base.get_primary_key table_name.to_s.singularize
|
209
|
-
end
|
205
|
+
if id && !td.as
|
206
|
+
pk = primary_key || Base.get_primary_key(table_name.to_s.singularize)
|
210
207
|
|
211
208
|
if pk.is_a?(Array)
|
212
209
|
td.primary_keys pk
|
213
210
|
else
|
214
|
-
td.primary_key pk,
|
211
|
+
td.primary_key pk, id, **options
|
215
212
|
end
|
216
213
|
end
|
217
214
|
|
@@ -229,8 +226,10 @@ module ActiveRecord
|
|
229
226
|
yield td if block_given?
|
230
227
|
create_sequence = create_sequence || td.create_sequence
|
231
228
|
|
232
|
-
if
|
233
|
-
drop_table(table_name,
|
229
|
+
if force && data_source_exists?(table_name)
|
230
|
+
drop_table(table_name, force: force, if_exists: true)
|
231
|
+
else
|
232
|
+
schema_cache.clear_data_source_cache!(table_name.to_s)
|
234
233
|
end
|
235
234
|
|
236
235
|
execute schema_creation.accept td
|
@@ -238,14 +237,14 @@ module ActiveRecord
|
|
238
237
|
create_sequence_and_trigger(table_name, options) if create_sequence
|
239
238
|
|
240
239
|
if supports_comments? && !supports_comments_in_create?
|
241
|
-
if table_comment =
|
240
|
+
if table_comment = td.comment.presence
|
242
241
|
change_table_comment(table_name, table_comment)
|
243
242
|
end
|
244
243
|
td.columns.each do |column|
|
245
244
|
change_column_comment(table_name, column.name, column.comment) if column.comment.present?
|
246
245
|
end
|
247
246
|
end
|
248
|
-
td.indexes.each { |c, o| add_index table_name, c, o }
|
247
|
+
td.indexes.each { |c, o| add_index table_name, c, **o }
|
249
248
|
|
250
249
|
rebuild_primary_key_index_to_default_tablespace(table_name, options)
|
251
250
|
end
|
@@ -254,13 +253,16 @@ module ActiveRecord
|
|
254
253
|
if new_name.to_s.length > DatabaseLimits::IDENTIFIER_MAX_LENGTH
|
255
254
|
raise ArgumentError, "New table name '#{new_name}' is too long; the limit is #{DatabaseLimits::IDENTIFIER_MAX_LENGTH} characters"
|
256
255
|
end
|
256
|
+
schema_cache.clear_data_source_cache!(table_name.to_s)
|
257
|
+
schema_cache.clear_data_source_cache!(new_name.to_s)
|
257
258
|
execute "RENAME #{quote_table_name(table_name)} TO #{quote_table_name(new_name)}"
|
258
259
|
execute "RENAME #{quote_table_name("#{table_name}_seq")} TO #{default_sequence_name(new_name)}" rescue nil
|
259
260
|
|
260
261
|
rename_table_indexes(table_name, new_name)
|
261
262
|
end
|
262
263
|
|
263
|
-
def drop_table(table_name, options
|
264
|
+
def drop_table(table_name, **options) #:nodoc:
|
265
|
+
schema_cache.clear_data_source_cache!(table_name.to_s)
|
264
266
|
execute "DROP TABLE #{quote_table_name(table_name)}#{' CASCADE CONSTRAINTS' if options[:force] == :cascade}"
|
265
267
|
seq_name = options[:sequence_name] || default_sequence_name(table_name)
|
266
268
|
execute "DROP SEQUENCE #{quote_table_name(seq_name)}" rescue nil
|
@@ -290,7 +292,7 @@ module ActiveRecord
|
|
290
292
|
end
|
291
293
|
end
|
292
294
|
|
293
|
-
def add_index(table_name, column_name, options
|
295
|
+
def add_index(table_name, column_name, **options) #:nodoc:
|
294
296
|
index_name, index_type, quoted_column_names, tablespace, index_options = add_index_options(table_name, column_name, **options)
|
295
297
|
execute "CREATE #{index_type} INDEX #{quote_column_name(index_name)} ON #{quote_table_name(table_name)} (#{quoted_column_names})#{tablespace} #{index_options}"
|
296
298
|
if index_type == "UNIQUE"
|
@@ -309,13 +311,11 @@ module ActiveRecord
|
|
309
311
|
index_type = options[:unique] ? "UNIQUE" : ""
|
310
312
|
index_name = options[:name].to_s if options.key?(:name)
|
311
313
|
tablespace = tablespace_for(:index, options[:tablespace])
|
312
|
-
|
313
|
-
# TODO: This option is used for NOLOGGING, needs better argumetn name
|
314
|
+
# TODO: This option is used for NOLOGGING, needs better argument name
|
314
315
|
index_options = options[:options]
|
315
316
|
|
316
|
-
|
317
|
-
|
318
|
-
end
|
317
|
+
validate_index_length!(table_name, index_name, options.fetch(:internal, false))
|
318
|
+
|
319
319
|
if table_exists?(table_name) && index_name_exists?(table_name, index_name)
|
320
320
|
raise ArgumentError, "Index name '#{index_name}' on table '#{table_name}' already exists"
|
321
321
|
end
|
@@ -326,8 +326,8 @@ module ActiveRecord
|
|
326
326
|
|
327
327
|
# Remove the given index from the table.
|
328
328
|
# Gives warning if index does not exist
|
329
|
-
def remove_index(table_name,
|
330
|
-
index_name = index_name_for_remove(table_name, options)
|
329
|
+
def remove_index(table_name, column_name = nil, **options) #:nodoc:
|
330
|
+
index_name = index_name_for_remove(table_name, column_name, options)
|
331
331
|
# TODO: It should execute only when index_type == "UNIQUE"
|
332
332
|
execute "ALTER TABLE #{quote_table_name(table_name)} DROP CONSTRAINT #{quote_column_name(index_name)}" rescue nil
|
333
333
|
execute "DROP INDEX #{quote_column_name(index_name)}"
|
@@ -364,8 +364,8 @@ module ActiveRecord
|
|
364
364
|
# Will always query database and not index cache.
|
365
365
|
def index_name_exists?(table_name, index_name)
|
366
366
|
(_owner, table_name) = @connection.describe(table_name)
|
367
|
-
result = select_value(<<~SQL.squish, "
|
368
|
-
SELECT
|
367
|
+
result = select_value(<<~SQL.squish, "SCHEMA")
|
368
|
+
SELECT 1 FROM all_indexes i
|
369
369
|
WHERE i.owner = SYS_CONTEXT('userenv', 'current_schema')
|
370
370
|
AND i.table_owner = SYS_CONTEXT('userenv', 'current_schema')
|
371
371
|
AND i.table_name = '#{table_name}'
|
@@ -443,7 +443,7 @@ module ActiveRecord
|
|
443
443
|
change_column table_name, column_name, column.sql_type, null: null
|
444
444
|
end
|
445
445
|
|
446
|
-
def change_column(table_name, column_name, type, options
|
446
|
+
def change_column(table_name, column_name, type, **options) #:nodoc:
|
447
447
|
column = column_for(table_name, column_name)
|
448
448
|
|
449
449
|
# remove :null option if its value is the same as current column definition
|
@@ -497,9 +497,10 @@ module ActiveRecord
|
|
497
497
|
end
|
498
498
|
|
499
499
|
def table_comment(table_name) #:nodoc:
|
500
|
+
# TODO
|
500
501
|
(_owner, table_name) = @connection.describe(table_name)
|
501
|
-
select_value(<<~SQL.squish, "
|
502
|
-
SELECT
|
502
|
+
select_value(<<~SQL.squish, "SCHEMA", [bind_string("table_name", table_name)])
|
503
|
+
SELECT comments FROM all_tab_comments
|
503
504
|
WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
504
505
|
AND table_name = :table_name
|
505
506
|
SQL
|
@@ -514,8 +515,8 @@ module ActiveRecord
|
|
514
515
|
def column_comment(table_name, column_name) #:nodoc:
|
515
516
|
# TODO: it does not exist in Abstract adapter
|
516
517
|
(_owner, table_name) = @connection.describe(table_name)
|
517
|
-
select_value(<<~SQL.squish, "
|
518
|
-
SELECT
|
518
|
+
select_value(<<~SQL.squish, "SCHEMA", [bind_string("table_name", table_name), bind_string("column_name", column_name.upcase)])
|
519
|
+
SELECT comments FROM all_col_comments
|
519
520
|
WHERE owner = SYS_CONTEXT('userenv', 'current_schema')
|
520
521
|
AND table_name = :table_name
|
521
522
|
AND column_name = :column_name
|
@@ -531,8 +532,8 @@ module ActiveRecord
|
|
531
532
|
end
|
532
533
|
|
533
534
|
def tablespace(table_name)
|
534
|
-
select_value(<<~SQL.squish, "
|
535
|
-
SELECT
|
535
|
+
select_value(<<~SQL.squish, "SCHEMA")
|
536
|
+
SELECT tablespace_name
|
536
537
|
FROM all_tables
|
537
538
|
WHERE table_name='#{table_name.to_s.upcase}'
|
538
539
|
AND owner = SYS_CONTEXT('userenv', 'current_schema')
|
@@ -543,8 +544,8 @@ module ActiveRecord
|
|
543
544
|
def foreign_keys(table_name) #:nodoc:
|
544
545
|
(_owner, desc_table_name) = @connection.describe(table_name)
|
545
546
|
|
546
|
-
fk_info = select_all(<<~SQL.squish, "
|
547
|
-
SELECT
|
547
|
+
fk_info = select_all(<<~SQL.squish, "SCHEMA", [bind_string("desc_table_name", desc_table_name)])
|
548
|
+
SELECT r.table_name to_table
|
548
549
|
,rc.column_name references_column
|
549
550
|
,cc.column_name
|
550
551
|
,c.constraint_name name
|
@@ -585,8 +586,8 @@ module ActiveRecord
|
|
585
586
|
# REFERENTIAL INTEGRITY ====================================
|
586
587
|
|
587
588
|
def disable_referential_integrity(&block) #:nodoc:
|
588
|
-
old_constraints = select_all(<<~SQL.squish, "
|
589
|
-
SELECT
|
589
|
+
old_constraints = select_all(<<~SQL.squish, "SCHEMA")
|
590
|
+
SELECT constraint_name, owner, table_name
|
590
591
|
FROM all_constraints
|
591
592
|
WHERE constraint_type = 'R'
|
592
593
|
AND status = 'ENABLED'
|
@@ -617,13 +618,12 @@ module ActiveRecord
|
|
617
618
|
end
|
618
619
|
|
619
620
|
private
|
620
|
-
|
621
621
|
def schema_creation
|
622
622
|
OracleEnhanced::SchemaCreation.new self
|
623
623
|
end
|
624
624
|
|
625
|
-
def create_table_definition(
|
626
|
-
OracleEnhanced::TableDefinition.new(self,
|
625
|
+
def create_table_definition(name, **options)
|
626
|
+
OracleEnhanced::TableDefinition.new(self, name, **options)
|
627
627
|
end
|
628
628
|
|
629
629
|
def new_column_from_field(table_name, field)
|
@@ -645,7 +645,7 @@ module ActiveRecord
|
|
645
645
|
# If a default contains a newline these cleanup regexes need to
|
646
646
|
# match newlines.
|
647
647
|
field["data_default"].sub!(/^'(.*)'$/m, '\1')
|
648
|
-
field["data_default"] = nil if
|
648
|
+
field["data_default"] = nil if /^(null|empty_[bc]lob\(\))$/i.match?(field["data_default"])
|
649
649
|
# TODO: Needs better fix to fallback "N" to false
|
650
650
|
field["data_default"] = false if field["data_default"] == "N" && OracleEnhancedAdapter.emulate_booleans_from_strings
|
651
651
|
end
|
@@ -702,7 +702,7 @@ module ActiveRecord
|
|
702
702
|
return unless tablespace
|
703
703
|
|
704
704
|
index_name = select_value(<<~SQL.squish, "Index name for primary key", [bind_string("table_name", table_name.upcase)])
|
705
|
-
SELECT
|
705
|
+
SELECT index_name FROM all_constraints
|
706
706
|
WHERE table_name = :table_name
|
707
707
|
AND constraint_type = 'P'
|
708
708
|
AND owner = SYS_CONTEXT('userenv', 'current_schema')
|