【问题标题】:In Mongoid, are there any differences in the Date, Time, DateTime, and TimeWithZone field types?在 Mongoid 中,Date、Time、DateTime 和 TimeWithZone 字段类型有什么区别吗?
【发布时间】:2013-12-24 07:16:16
【问题描述】:

文档中提到了四种时间相关字段类型 (http://mongoid.org/en/mongoid/docs/documents.html#fields)。在其他数据库中,我可以看到这些字段将如何成为数据库中的不同类型,但对于 MongoDB,它们不都是日期类型吗?这只是为了与 ActiveRecord 保持一致吗?

【问题讨论】:

    标签: ruby-on-rails mongodb


    【解决方案1】:

    它们几乎没有区别,都是包裹Time类型的。 从 mongo 反序列化后,您可以更改 DateTime、Date 或 TimeWithZone 以获取此类型的实例。

    Mongoid 扩展了这些类,为数据绑定添加了 demogoize/mongoize 方法。所以唯一的区别是在实现上。

    所以时间实现

    def demongoize(object)
      return nil if object.blank?
      object = object.getlocal unless Mongoid::Config.use_utc?
      if Mongoid::Config.use_activesupport_time_zone?
        object = object.in_time_zone(Mongoid.time_zone)
      end
      object
    end
    
    def mongoize(object)
      return nil if object.blank?
      begin
        time = object.__mongoize_time__
        if object.respond_to?(:sec_fraction)
          ::Time.at(time.to_i, object.sec_fraction * 10**6).utc
        elsif time.respond_to?(:subsec)
          ::Time.at(time.to_i, time.subsec * 10**6).utc
        else
          ::Time.at(time.to_i, time.usec).utc
        end
      rescue ArgumentError
        EPOCH
      end
    end
    

    实施日期

    def demongoize(object)
      ::Date.new(object.year, object.month, object.day) if object
    end
    
    
    def mongoize(object)
      unless object.blank?
        begin
          time = object.__mongoize_time__
          ::Time.utc(time.year, time.month, time.day)
        rescue ArgumentError
          EPOCH
        end
      end
    end
    

    您可以检查其他实现

    https://github.com/mongoid/mongoid/blob/master/lib/mongoid/extensions/date.rb#L46 https://github.com/mongoid/mongoid/blob/master/lib/mongoid/extensions/date_time.rb#L49 https://github.com/mongoid/mongoid/blob/master/lib/mongoid/extensions/time.rb#L48 https://github.com/mongoid/mongoid/blob/master/lib/mongoid/extensions/time_with_zone.rb#L32

    【讨论】:

    • 只是一个警告:我在 rspec 测试中观察到一个奇怪的错误,其中 DateTime 字段上的断言有时会因为毫秒差异而失败。我在使用时间类型或在断言之前系统地重新加载对象时没有这个问题。
    • 这个答案在 Mongoid 6.2 中是不正确的。 Mongoid 的Time 数据类型用于存储ActiveSupport::TimeWithZone,而DateTime 是纯Ruby DateTime。这两者之间有重要的区别。
    猜你喜欢
    • 1970-01-01
    • 2011-04-25
    • 2011-03-19
    • 1970-01-01
    • 1970-01-01
    • 2010-11-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多