activerecord-sqlserver-adapter 4.2.6 → 4.2.8
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +34 -0
- data/Gemfile +9 -0
- data/README.md +40 -26
- data/VERSION +1 -0
- data/activerecord-sqlserver-adapter.gemspec +0 -10
- data/appveyor.yml +15 -3
- data/lib/active_record/connection_adapters/sqlserver/database_statements.rb +3 -3
- data/lib/active_record/connection_adapters/sqlserver/database_tasks.rb +35 -11
- data/lib/active_record/connection_adapters/sqlserver/quoting.rb +4 -16
- data/lib/active_record/connection_adapters/sqlserver/schema_statements.rb +12 -2
- data/lib/active_record/connection_adapters/sqlserver/table_definition.rb +8 -0
- data/lib/active_record/connection_adapters/sqlserver/type.rb +3 -1
- data/lib/active_record/connection_adapters/sqlserver/type/date.rb +9 -0
- data/lib/active_record/connection_adapters/sqlserver/type/datetime.rb +18 -12
- data/lib/active_record/connection_adapters/sqlserver/type/datetime2.rb +17 -0
- data/lib/active_record/connection_adapters/sqlserver/type/datetimeoffset.rb +31 -0
- data/lib/active_record/connection_adapters/sqlserver/type/smalldatetime.rb +6 -6
- data/lib/active_record/connection_adapters/sqlserver/type/time.rb +13 -29
- data/lib/active_record/connection_adapters/sqlserver/type/time_value_fractional.rb +72 -0
- data/lib/active_record/connection_adapters/sqlserver/utils.rb +12 -12
- data/lib/active_record/connection_adapters/sqlserver/version.rb +1 -1
- data/lib/active_record/connection_adapters/sqlserver_adapter.rb +41 -5
- data/lib/active_record/sqlserver_base.rb +2 -4
- data/lib/arel/visitors/sqlserver.rb +19 -0
- data/test/cases/adapter_test_sqlserver.rb +24 -0
- data/test/cases/coerced_tests.rb +14 -0
- data/test/cases/column_test_sqlserver.rb +120 -47
- data/test/cases/connection_test_sqlserver.rb +3 -3
- data/test/cases/fully_qualified_identifier_test_sqlserver.rb +76 -0
- data/test/cases/helper_sqlserver.rb +24 -16
- data/test/cases/migration_test_sqlserver.rb +0 -5
- data/test/cases/rake_test_sqlserver.rb +29 -10
- data/test/cases/schema_dumper_test_sqlserver.rb +28 -11
- data/test/cases/transaction_test_sqlserver.rb +2 -2
- data/test/cases/utils_test_sqlserver.rb +44 -14
- data/test/config.yml +2 -0
- data/test/debug.rb +14 -0
- data/test/schema/datatypes/2012.sql +8 -18
- data/test/schema/sqlserver_specific_schema.rb +14 -12
- data/test/support/connection_reflection.rb +37 -0
- metadata +13 -143
- data/lib/active_record/connection_adapters/sqlserver/type/quoter.rb +0 -32
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6f37e4ce81b63e3fe3375111b70da855a95d1251
|
4
|
+
data.tar.gz: 7b11a582736c9718dbb20097b0b55c392f691b08
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: f0066beca8922fb26506304059d80069a91f45b9392857e68a2af63640f4706ff300ca4b8e8bb18d807117bb168039188d50d397897488de255b31c454692a1c
|
7
|
+
data.tar.gz: e52261a203dcc9d9124ed6d04113fbcc15887e09b38f18076e213906da9b2b4fbf71e83032b5ee284483c206a28d9bb237f6f04e67cbdcc7e0b68ece791f8fbb
|
data/CHANGELOG.md
CHANGED
@@ -1,4 +1,38 @@
|
|
1
1
|
|
2
|
+
## v4.2.8
|
3
|
+
|
4
|
+
#### Fixed
|
5
|
+
|
6
|
+
* Azure-Friendly Disable Referential Integrity. No more `sp_MSforeachtable` usage. Fixes #421
|
7
|
+
* Azure-Friendly DB create/drop. Fixes #442
|
8
|
+
- Create allows edition options like: MAXSIZE, EDITION, and SERVICE_OBJECTIVE.
|
9
|
+
|
10
|
+
|
11
|
+
## v4.2.7
|
12
|
+
|
13
|
+
#### Added
|
14
|
+
|
15
|
+
* Support 2008 Datatypes Using TDSVER=7.3. Fixes #433
|
16
|
+
|
17
|
+
#### Changed
|
18
|
+
|
19
|
+
* Test now use latest v0.9.5 of TinyTDS. Includes tests for `defncopy` Windows binstub.
|
20
|
+
* Make linked servers stronger. Fixes #427. Thanks @jippeholwerda
|
21
|
+
* Use proper module for the `sqlserver_connection` method. Fixes #431. Thanks @jippeholwerda
|
22
|
+
* All datetime casting using the `Time::DATE_FORMATS[:_sqlserver_*]` formats set after connection.
|
23
|
+
|
24
|
+
#### Removed
|
25
|
+
|
26
|
+
* The `SQLServer::Utils.with_sqlserver_db_date_formats` helper and `quoted_date` hacks.
|
27
|
+
* The `Quoter` value type which allowed column => type special case quoting.
|
28
|
+
|
29
|
+
#### Fixed
|
30
|
+
|
31
|
+
* Every time datatype has perfect micro/nano second handling.
|
32
|
+
* All supported datatypes dump defaults properly to schema.rb
|
33
|
+
* Partial indexes using `:where` in schema dumper. Fixes #153
|
34
|
+
|
35
|
+
|
2
36
|
## v4.2.6
|
3
37
|
|
4
38
|
#### Fixed
|
data/Gemfile
CHANGED
@@ -37,6 +37,8 @@ end
|
|
37
37
|
group :tinytds do
|
38
38
|
if ENV['TINYTDS_SOURCE']
|
39
39
|
gem 'tiny_tds', path: ENV['TINYTDS_SOURCE']
|
40
|
+
elsif ENV['TINYTDS_VERSION']
|
41
|
+
gem 'tiny_tds', ENV['TINYTDS_VERSION']
|
40
42
|
else
|
41
43
|
gem 'tiny_tds'
|
42
44
|
end
|
@@ -46,3 +48,10 @@ group :odbc do
|
|
46
48
|
gem 'ruby-odbc'
|
47
49
|
end
|
48
50
|
|
51
|
+
group :development do
|
52
|
+
gem 'guard'
|
53
|
+
gem 'guard-minitest'
|
54
|
+
gem 'mocha'
|
55
|
+
gem 'minitest', '< 5.3.4' # PENDING: [Rails5.x] Remove test order constraint.
|
56
|
+
gem 'minitest-spec-rails'
|
57
|
+
end
|
data/README.md
CHANGED
@@ -25,36 +25,50 @@ Account.execute_procedure :update_totals, named: 'params'
|
|
25
25
|
|
26
26
|
#### Native Data Type Support
|
27
27
|
|
28
|
-
We support every data type supported by FreeTDS and then a few more. All simplified Rails types in migrations will coorespond to a matching SQL Server national data type. Here is a basic chart. Always check the `initialize_native_database_types` method for an updated list.
|
28
|
+
We support every data type supported by FreeTDS and then a few more. All simplified Rails types in migrations will coorespond to a matching SQL Server national (unicode) data type. Here is a basic chart. Always check the `initialize_native_database_types` method for an updated list.
|
29
29
|
|
30
30
|
```ruby
|
31
|
-
integer:
|
32
|
-
bigint:
|
33
|
-
boolean:
|
34
|
-
decimal:
|
35
|
-
money:
|
36
|
-
smallmoney:
|
37
|
-
float:
|
38
|
-
real:
|
39
|
-
date:
|
40
|
-
datetime:
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
31
|
+
integer: { name: 'int', limit: 4 }
|
32
|
+
bigint: { name: 'bigint' }
|
33
|
+
boolean: { name: 'bit' }
|
34
|
+
decimal: { name: 'decimal' }
|
35
|
+
money: { name: 'money' }
|
36
|
+
smallmoney: { name: 'smallmoney' }
|
37
|
+
float: { name: 'float' }
|
38
|
+
real: { name: 'real' }
|
39
|
+
date: { name: 'date' }
|
40
|
+
datetime: { name: 'datetime' }
|
41
|
+
datetime2: { name: 'datetime2', precision: 7 }
|
42
|
+
datetimeoffset: { name: 'datetimeoffset', precision: 7 }
|
43
|
+
smalldatetime: { name: 'smalldatetime' }
|
44
|
+
timestamp: { name: 'datetime' }
|
45
|
+
time: { name: 'time' }
|
46
|
+
char: { name: 'char' }
|
47
|
+
varchar: { name: 'varchar', limit: 8000 }
|
48
|
+
varchar_max: { name: 'varchar(max)' }
|
49
|
+
text_basic: { name: 'text' }
|
50
|
+
nchar: { name: 'nchar' }
|
51
|
+
string: { name: 'nvarchar', limit: 4000 }
|
52
|
+
text: { name: 'nvarchar(max)' }
|
53
|
+
ntext: { name: 'ntext' }
|
54
|
+
binary_basic: { name: 'binary' }
|
55
|
+
varbinary: { name: 'varbinary', limit: 8000 }
|
56
|
+
binary: { name: 'varbinary(max)' }
|
57
|
+
uuid: { name: 'uniqueidentifier' }
|
58
|
+
ss_timestamp: { name: 'timestamp' }
|
56
59
|
```
|
57
60
|
|
61
|
+
The following types require TDS version 7.3 with TinyTDS. This requires the latest FreeTDS v0.95 or higher.
|
62
|
+
|
63
|
+
* date
|
64
|
+
* datetime2
|
65
|
+
* datetimeoffset
|
66
|
+
* time
|
67
|
+
|
68
|
+
Set `tds_version` in your database.yml or the `TDSVER` environment variable to `7.3` to ensure you are using the proper protocol version till 7.3 becomes the default.
|
69
|
+
|
70
|
+
**Zone Conversion** - The `[datetimeoffset]` type is the only ActiveRecord time based datatype that does not cast the zone to ActiveRecord's default - typically UTC. As intended, this datatype is meant to maintain the zone you pass to it and/or retreived from the database.
|
71
|
+
|
58
72
|
|
59
73
|
#### Force Schema To Lowercase
|
60
74
|
|
data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
4.2.8
|
@@ -17,14 +17,4 @@ Gem::Specification.new do |spec|
|
|
17
17
|
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
18
18
|
spec.require_paths = ['lib']
|
19
19
|
spec.add_dependency 'activerecord', '~> 4.2.1'
|
20
|
-
spec.add_development_dependency 'bundler'
|
21
|
-
spec.add_development_dependency 'guard'
|
22
|
-
spec.add_development_dependency 'guard-minitest'
|
23
|
-
spec.add_development_dependency 'minitest', '< 5.3.4' # PENDING: [Rails5.x] Remove test order constraint.
|
24
|
-
spec.add_development_dependency 'minitest-focus'
|
25
|
-
spec.add_development_dependency 'minitest-spec-rails'
|
26
|
-
spec.add_development_dependency 'mocha'
|
27
|
-
spec.add_development_dependency 'nokogiri'
|
28
|
-
spec.add_development_dependency 'byebug'
|
29
|
-
spec.add_development_dependency 'rake'
|
30
20
|
end
|
data/appveyor.yml
CHANGED
@@ -1,13 +1,14 @@
|
|
1
|
-
version: 4.2.5.{build}
|
2
1
|
init:
|
3
2
|
- SET PATH=C:\Ruby%ruby_version%\bin;%PATH%
|
4
3
|
- SET PATH=C:\MinGW\msys\1.0\bin;%PATH%
|
5
4
|
- SET RAKEOPT=-rdevkit
|
5
|
+
- SET TINYTDS_VERSION=0.9.5.rc.3
|
6
6
|
clone_depth: 5
|
7
7
|
skip_tags: true
|
8
8
|
matrix:
|
9
9
|
fast_finish: true
|
10
10
|
install:
|
11
|
+
- ps: Update-AppveyorBuild -Version "$(Get-Content $env:appveyor_build_folder\VERSION).$env:appveyor_build_number"
|
11
12
|
- ruby --version
|
12
13
|
- gem --version
|
13
14
|
- bundle install --without odbc
|
@@ -19,12 +20,23 @@ test_script:
|
|
19
20
|
- timeout /t 4 /nobreak > NUL
|
20
21
|
- sqlcmd -S ".\SQL2014" -U sa -P Password12! -i %APPVEYOR_BUILD_FOLDER%\test\appveyor\dbsetup.sql
|
21
22
|
- bundle exec rake test ACTIVERECORD_UNITTEST_DATASERVER="localhost\SQL2014"
|
23
|
+
- bundle exec rake test ACTIVERECORD_UNITTEST_DATASERVER="localhost\SQL2014" ACTIVERECORD_UNITTEST_TDSVERSION="7.3"
|
22
24
|
- ps: Stop-Service 'MSSQL$SQL2014'
|
23
25
|
- ps: Start-Service 'MSSQL$SQL2012SP1'
|
24
26
|
- timeout /t 4 /nobreak > NUL
|
25
27
|
- sqlcmd -S ".\SQL2012SP1" -U sa -P Password12! -i %APPVEYOR_BUILD_FOLDER%\test\appveyor\dbsetup.sql
|
26
28
|
- bundle exec rake test ACTIVERECORD_UNITTEST_DATASERVER="localhost\SQL2012SP1"
|
29
|
+
- bundle exec rake test ACTIVERECORD_UNITTEST_DATASERVER="localhost\SQL2012SP1" ACTIVERECORD_UNITTEST_TDSVERSION="7.3"
|
30
|
+
# - timeout /t 4 /nobreak > NUL
|
31
|
+
# - bundle exec rake test ACTIVERECORD_UNITTEST_HOST=%CI_AZURE_HOST% ACTIVERECORD_UNITTEST_PASS=%CI_AZURE_PASS% ACTIVERECORD_UNITTEST_AZURE=1
|
32
|
+
# - timeout /t 4 /nobreak > NUL
|
33
|
+
# - bundle exec rake test ACTIVERECORD_UNITTEST_HOST=%CI_AZURE_HOST% ACTIVERECORD_UNITTEST_PASS=%CI_AZURE_PASS% ACTIVERECORD_UNITTEST_AZURE=1 TDSVER=7.3
|
27
34
|
environment:
|
35
|
+
CI_AZURE_HOST:
|
36
|
+
secure: VChrioaIWkf9iuuaSs4cryiA4honrADgZqNC0++begg=
|
37
|
+
CI_AZURE_PASS:
|
38
|
+
secure: cSQp8sk4urJYvq0utpsK+r7J+snJ2wpcdp8RdXJfB+w=
|
28
39
|
matrix:
|
29
|
-
- ruby_version: "200
|
30
|
-
- ruby_version: "
|
40
|
+
- ruby_version: "200"
|
41
|
+
- ruby_version: "22"
|
42
|
+
- ruby_version: "22-x64"
|
@@ -179,8 +179,8 @@ module ActiveRecord
|
|
179
179
|
if sqlserver_azure?
|
180
180
|
sql = %(SELECT CASE [transaction_isolation_level]
|
181
181
|
WHEN 0 THEN NULL
|
182
|
-
WHEN 1 THEN 'READ
|
183
|
-
WHEN 2 THEN 'READ
|
182
|
+
WHEN 1 THEN 'READ UNCOMMITTED'
|
183
|
+
WHEN 2 THEN 'READ COMMITTED'
|
184
184
|
WHEN 3 THEN 'REPEATABLE READ'
|
185
185
|
WHEN 4 THEN 'SERIALIZABLE'
|
186
186
|
WHEN 5 THEN 'SNAPSHOT' END AS [isolation_level]
|
@@ -216,7 +216,7 @@ module ActiveRecord
|
|
216
216
|
end
|
217
217
|
|
218
218
|
def sql_for_insert(sql, pk, id_value, sequence_name, binds)
|
219
|
-
sql = if pk && self.class.use_output_inserted
|
219
|
+
sql = if pk && self.class.use_output_inserted && !database_prefix_remote_server?
|
220
220
|
quoted_pk = SQLServer::Utils.extract_identifiers(pk).quoted
|
221
221
|
sql.insert sql.index(/ (DEFAULT )?VALUES/), " OUTPUT INSERTED.#{quoted_pk}"
|
222
222
|
else
|
@@ -5,17 +5,9 @@ module ActiveRecord
|
|
5
5
|
|
6
6
|
def create_database(database, options = {})
|
7
7
|
name = SQLServer::Utils.extract_identifiers(database)
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
memo += case key
|
12
|
-
when :collation
|
13
|
-
" COLLATE #{value}"
|
14
|
-
else
|
15
|
-
""
|
16
|
-
end
|
17
|
-
end
|
18
|
-
do_execute "CREATE DATABASE #{name}#{option_string}"
|
8
|
+
db_options = create_database_options(options)
|
9
|
+
edition_options = create_database_edition_options(options)
|
10
|
+
do_execute "CREATE DATABASE #{name} #{db_options} #{edition_options}"
|
19
11
|
end
|
20
12
|
|
21
13
|
def drop_database(database)
|
@@ -35,6 +27,38 @@ module ActiveRecord
|
|
35
27
|
select_value "SELECT DATABASEPROPERTYEX(DB_NAME(), 'Collation')"
|
36
28
|
end
|
37
29
|
|
30
|
+
|
31
|
+
private
|
32
|
+
|
33
|
+
def create_database_options(options={})
|
34
|
+
keys = [:collate]
|
35
|
+
copts = @connection_options
|
36
|
+
options = {
|
37
|
+
collate: copts[:collation]
|
38
|
+
}.merge(options.symbolize_keys).select { |_, v|
|
39
|
+
v.present?
|
40
|
+
}.slice(*keys).map { |k,v|
|
41
|
+
"#{k.to_s.upcase} #{v}"
|
42
|
+
}.join(' ')
|
43
|
+
options
|
44
|
+
end
|
45
|
+
|
46
|
+
def create_database_edition_options(options={})
|
47
|
+
keys = [:maxsize, :edition, :service_objective]
|
48
|
+
copts = @connection_options
|
49
|
+
edition_options = {
|
50
|
+
maxsize: copts[:azure_maxsize],
|
51
|
+
edition: copts[:azure_edition],
|
52
|
+
service_objective: copts[:azure_service_objective]
|
53
|
+
}.merge(options.symbolize_keys).select { |_, v|
|
54
|
+
v.present?
|
55
|
+
}.slice(*keys).map { |k,v|
|
56
|
+
"#{k.to_s.upcase} = #{v}"
|
57
|
+
}.join(', ')
|
58
|
+
edition_options = "( #{edition_options} )" if edition_options.present?
|
59
|
+
edition_options
|
60
|
+
end
|
61
|
+
|
38
62
|
end
|
39
63
|
end
|
40
64
|
end
|
@@ -40,15 +40,10 @@ module ActiveRecord
|
|
40
40
|
end
|
41
41
|
|
42
42
|
def quoted_date(value)
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
elsif value.acts_like?(:date)
|
48
|
-
value.to_s(:_sqlserver_dateformat)
|
49
|
-
else
|
50
|
-
super
|
51
|
-
end
|
43
|
+
if value.acts_like?(:date)
|
44
|
+
Type::Date.new.type_cast_for_database(value)
|
45
|
+
else value.acts_like?(:time)
|
46
|
+
Type::DateTime.new.type_cast_for_database(value)
|
52
47
|
end
|
53
48
|
end
|
54
49
|
|
@@ -59,8 +54,6 @@ module ActiveRecord
|
|
59
54
|
case value
|
60
55
|
when Type::Binary::Data
|
61
56
|
"0x#{value.hex}"
|
62
|
-
when SQLServer::Type::Quoter
|
63
|
-
value.quote_ss_value
|
64
57
|
when String, ActiveSupport::Multibyte::Chars
|
65
58
|
if value.is_utf8?
|
66
59
|
"#{QUOTED_STRING_PREFIX}#{super}"
|
@@ -72,11 +65,6 @@ module ActiveRecord
|
|
72
65
|
end
|
73
66
|
end
|
74
67
|
|
75
|
-
def quoted_value_acts_like_time_filter(value)
|
76
|
-
zone_conversion_method = ActiveRecord::Base.default_timezone == :utc ? :getutc : :getlocal
|
77
|
-
value.respond_to?(zone_conversion_method) ? value.send(zone_conversion_method) : value
|
78
|
-
end
|
79
|
-
|
80
68
|
end
|
81
69
|
end
|
82
70
|
end
|
@@ -32,12 +32,13 @@ module ActiveRecord
|
|
32
32
|
else
|
33
33
|
name = index[:index_name]
|
34
34
|
unique = index[:index_description] =~ /unique/
|
35
|
+
where = select_value("SELECT [filter_definition] FROM sys.indexes WHERE name = #{quote(name)}")
|
35
36
|
columns = index[:index_keys].split(',').map do |column|
|
36
37
|
column.strip!
|
37
38
|
column.gsub! '(-)', '' if column.ends_with?('(-)')
|
38
39
|
column
|
39
40
|
end
|
40
|
-
indexes << IndexDefinition.new(table_name, name, unique, columns)
|
41
|
+
indexes << IndexDefinition.new(table_name, name, unique, columns, nil, nil, where)
|
41
42
|
end
|
42
43
|
end
|
43
44
|
end
|
@@ -201,6 +202,9 @@ module ActiveRecord
|
|
201
202
|
real: { name: 'real' },
|
202
203
|
date: { name: 'date' },
|
203
204
|
datetime: { name: 'datetime' },
|
205
|
+
datetime2: { name: 'datetime2' },
|
206
|
+
datetimeoffset: { name: 'datetimeoffset' },
|
207
|
+
smalldatetime: { name: 'smalldatetime' },
|
204
208
|
timestamp: { name: 'datetime' },
|
205
209
|
time: { name: 'time' },
|
206
210
|
char: { name: 'char' },
|
@@ -220,7 +224,11 @@ module ActiveRecord
|
|
220
224
|
end
|
221
225
|
|
222
226
|
def column_definitions(table_name)
|
223
|
-
identifier
|
227
|
+
identifier = if database_prefix_remote_server?
|
228
|
+
SQLServer::Utils.extract_identifiers("#{database_prefix}#{table_name}")
|
229
|
+
else
|
230
|
+
SQLServer::Utils.extract_identifiers(table_name)
|
231
|
+
end
|
224
232
|
database = identifier.fully_qualified_database_quoted
|
225
233
|
view_exists = schema_cache.view_exists?(table_name)
|
226
234
|
view_tblnm = table_name_or_views_table_name(table_name) if view_exists
|
@@ -282,6 +290,8 @@ module ActiveRecord
|
|
282
290
|
ci[:type] = case ci[:type]
|
283
291
|
when /^bit|image|text|ntext|datetime$/
|
284
292
|
ci[:type]
|
293
|
+
when /^datetime2|datetimeoffset$/i
|
294
|
+
"#{ci[:type]}(#{ci[:datetime_precision]})"
|
285
295
|
when /^time$/i
|
286
296
|
"#{ci[:type]}(#{ci[:datetime_precision]})"
|
287
297
|
when /^numeric|decimal$/i
|
@@ -18,6 +18,14 @@ module ActiveRecord
|
|
18
18
|
column(name, :money, options)
|
19
19
|
end
|
20
20
|
|
21
|
+
def datetime2(name, options = {})
|
22
|
+
column(name, :datetime2, options)
|
23
|
+
end
|
24
|
+
|
25
|
+
def datetimeoffset(name, options = {})
|
26
|
+
column(name, :datetimeoffset, options)
|
27
|
+
end
|
28
|
+
|
21
29
|
def smallmoney(name, options = {})
|
22
30
|
column(name, :smallmoney, options)
|
23
31
|
end
|
@@ -1,5 +1,4 @@
|
|
1
1
|
require 'active_record/type'
|
2
|
-
require 'active_record/connection_adapters/sqlserver/type/quoter.rb'
|
3
2
|
# Exact Numerics
|
4
3
|
require 'active_record/connection_adapters/sqlserver/type/integer.rb'
|
5
4
|
require 'active_record/connection_adapters/sqlserver/type/big_integer.rb'
|
@@ -13,8 +12,11 @@ require 'active_record/connection_adapters/sqlserver/type/small_money.rb'
|
|
13
12
|
require 'active_record/connection_adapters/sqlserver/type/float.rb'
|
14
13
|
require 'active_record/connection_adapters/sqlserver/type/real.rb'
|
15
14
|
# Date and Time
|
15
|
+
require 'active_record/connection_adapters/sqlserver/type/time_value_fractional.rb'
|
16
16
|
require 'active_record/connection_adapters/sqlserver/type/date.rb'
|
17
17
|
require 'active_record/connection_adapters/sqlserver/type/datetime.rb'
|
18
|
+
require 'active_record/connection_adapters/sqlserver/type/datetime2.rb'
|
19
|
+
require 'active_record/connection_adapters/sqlserver/type/datetimeoffset.rb'
|
18
20
|
require 'active_record/connection_adapters/sqlserver/type/smalldatetime.rb'
|
19
21
|
require 'active_record/connection_adapters/sqlserver/type/time.rb'
|
20
22
|
# Character Strings
|
@@ -4,6 +4,15 @@ module ActiveRecord
|
|
4
4
|
module Type
|
5
5
|
class Date < ActiveRecord::Type::Date
|
6
6
|
|
7
|
+
def type_cast_for_database(value)
|
8
|
+
return unless value.present?
|
9
|
+
return value if value.acts_like?(:string)
|
10
|
+
value.to_s(:_sqlserver_dateformat)
|
11
|
+
end
|
12
|
+
|
13
|
+
def type_cast_for_schema(value)
|
14
|
+
type_cast_for_database(value).inspect
|
15
|
+
end
|
7
16
|
|
8
17
|
end
|
9
18
|
end
|
@@ -4,28 +4,34 @@ module ActiveRecord
|
|
4
4
|
module Type
|
5
5
|
class DateTime < ActiveRecord::Type::DateTime
|
6
6
|
|
7
|
+
include TimeValueFractional
|
8
|
+
|
9
|
+
def type_cast_for_database(value)
|
10
|
+
return super unless value.acts_like?(:time)
|
11
|
+
value = zone_conversion(value)
|
12
|
+
datetime = value.to_s(:_sqlserver_datetime)
|
13
|
+
"#{datetime}".tap do |v|
|
14
|
+
fraction = quote_fractional(value)
|
15
|
+
v << ".#{fraction}" unless fraction.to_i.zero?
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
7
19
|
def type_cast_for_schema(value)
|
8
|
-
value.
|
20
|
+
type_cast_for_database(value).inspect
|
9
21
|
end
|
10
22
|
|
11
23
|
|
12
24
|
private
|
13
25
|
|
14
26
|
def cast_value(value)
|
15
|
-
value = value.
|
27
|
+
value = value.acts_like?(:time) ? value : super
|
16
28
|
return unless value
|
17
|
-
|
18
|
-
end
|
19
|
-
|
20
|
-
def cast_usec(value)
|
21
|
-
return 0 if !value.respond_to?(:usec) || value.usec.zero?
|
22
|
-
seconds = value.usec.to_f / 1_000_000.0
|
23
|
-
ss_seconds = ((seconds * (1 / second_precision)).round / (1 / second_precision)).round(3)
|
24
|
-
(ss_seconds * 1_000_000).to_i
|
29
|
+
cast_fractional(value)
|
25
30
|
end
|
26
31
|
|
27
|
-
def
|
28
|
-
|
32
|
+
def zone_conversion(value)
|
33
|
+
method = ActiveRecord::Base.default_timezone == :utc ? :getutc : :getlocal
|
34
|
+
value.respond_to?(method) ? value.send(method) : value
|
29
35
|
end
|
30
36
|
|
31
37
|
end
|