Skip to content

Commit

Permalink
opt out of truncating times (#72)
Browse files Browse the repository at this point in the history
  • Loading branch information
mnelson authored Nov 22, 2024
1 parent 6aeeb22 commit 0bf4537
Show file tree
Hide file tree
Showing 3 changed files with 22 additions and 18 deletions.
8 changes: 8 additions & 0 deletions lib/subroutine.rb
Original file line number Diff line number Diff line change
Expand Up @@ -33,4 +33,12 @@ def self.inheritable_field_options
@inheritable_field_options ||= %i[mass_assignable field_reader field_writer groups aka]
end

def self.preserve_time_precision=(bool)
@preserve_time_precision = !!bool
end

def self.preserve_time_precision?
!!@preserve_time_precision
end

end
26 changes: 11 additions & 15 deletions lib/subroutine/type_caster.rb
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
require 'time'
require 'bigdecimal'
require 'securerandom'
require 'active_support/json'
require 'active_support/core_ext/date_time/acts_like'
require 'active_support/core_ext/date_time/calculations'
require 'active_support/core_ext/object/acts_like'
Expand Down Expand Up @@ -111,7 +112,7 @@ def self.cast(value, options = {})
t ||= value if value.is_a?(::Time)
t ||= value if value.try(:acts_like?, :time)
t ||= ::Time.parse(String(value))
t.utc.iso8601
t.utc.iso8601(::ActiveSupport::JSON::Encoding.time_precision)
end

::Subroutine::TypeCaster.register :date do |value, _options = {}|
Expand All @@ -123,21 +124,16 @@ def self.cast(value, options = {})
::Subroutine::TypeCaster.register :time, :timestamp, :datetime do |value, options = {}|
next nil unless value.present?

if options[:precision] == :high
if value.try(:acts_like?, :time)
value.to_time
else
::Time.parse(String(value))
end
else # precision == :seconds
time = if value.try(:acts_like?, :time)
value.to_time
else
::Time.parse(String(value))
end

time.change(usec: 0)
value = if value.try(:acts_like?, :time)
value.to_time
else
::Time.parse(String(value))
end

# High precision must be opted into. The original implementation is to set usec:0
next value if options[:precision] == :high || ::Subroutine.preserve_time_precision?

value.change(usec: 0)
end

::Subroutine::TypeCaster.register :hash, :object, :hashmap, :dict do |value, _options = {}|
Expand Down
6 changes: 3 additions & 3 deletions test/subroutine/type_caster_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -438,11 +438,11 @@ def test_iso_time_inputs

op.iso_time_input = '2022-12-22T10:30:24Z'
assert_equal ::String, op.iso_time_input.class
assert_equal '2022-12-22T10:30:24Z', op.iso_time_input
assert_equal '2022-12-22T10:30:24.000Z', op.iso_time_input

op.iso_time_input = Time.parse('2022-12-22T10:30:24Z')
op.iso_time_input = Time.parse('2022-12-22T10:30:24.123456Z')
assert_equal ::String, op.iso_time_input.class
assert_equal '2022-12-22T10:30:24Z', op.iso_time_input
assert_equal '2022-12-22T10:30:24.123Z', op.iso_time_input
end

def test_file_inputs
Expand Down

0 comments on commit 0bf4537

Please sign in to comment.