如何使用 Ruby on Rails 中的映射表跟踪模型历史? [英] How to keep track of model history with mapping table in Ruby on Rails?

查看:14
本文介绍了如何使用 Ruby on Rails 中的映射表跟踪模型历史?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想记录用户何时更改地址.

I'd like to keep record of when a user changes their address.

这样,当下单时,它总是能够引用下单时使用的用户地址.

This way, when an order is placed, it will always be able to reference the user address that was used at the time of order placement.

users (
  id
  username
  email
  ...
)

user_addresses (
  id
  label
  line_1
  line_2
  city
  state
  zip
  ...
)

user_addresses_map (
  user_id
  user_address_id
  start_time
  end_time
)

orders (
  id
  user_id
  user_address_id
  order_status_id
  ...
  created_at
  updated_at
)

在 sql 中,这可能类似于:[sql]

select ua.*

from  orders    o

join  users     u
  on  u.id = o.user_id
  
join  user_addressses_map   uam
  on  uam.user_id = u.id
  and uam.user_address_id = o.user_address_id
  
join  user_addresses        ua
  on  ua.id = uam.user_address_id
  and uam.start_time < o.created_at
  and (uam.end_time >= o.created_at or uam.end_time is null)
;

解决方案

@KandadaBoggu 发布了一个很好的解决方案.Vestal Versions 插件 是一个很好的解决方案.

下面摘自 http://github.com/laserlemon/vestal_versions

acts_as_versioned 来自 technoweenie 是一个很好的开始,但它未能跟上 ActiveRecord 在 2.1 版中引入的脏对象.此外,每个版本化模型都需要自己的版本表来复制原始表的大部分列.然后,版本表中填充了通常复制大部分原始记录属性的记录.总而言之,不是很干.

acts_as_versioned by technoweenie was a great start, but it failed to keep up with ActiveRecord’s introduction of dirty objects in version 2.1. Additionally, each versioned model needs its own versions table that duplicates most of the original table’s columns. The versions table is then populated with records that often duplicate most of the original record’s attributes. All in all, not very DRY.

vestal_versions 只需要一个版本表(与其父模型多态关联)并且对现有的没有任何改变表.但它通过存储模型更改的序列化哈希值,使 DRYer 更进一步.想想现代版本控制系统.通过遍历变更记录,可以将模型恢复到任意时间点.

vestal_versions requires only one versions table (polymorphically associated with its parent models) and no changes whatsoever to existing tables. But it goes one step DRYer by storing a serialized hash of only the models’ changes. Think modern version control systems. By traversing the record of changes, the models can be reverted to any point in time.

这正是 Vental_versions 所做的.模型不仅可以恢复到以前的版本号,还可以恢复到日期或时间!

And that’s just what vestal_versions does. Not only can a model be reverted to a previous version number but also to a date or time!

推荐答案

使用 Vestal 版本插件这个:

有关详细信息,请参阅截屏.

Refer to this screen cast for more details.

class Address < ActiveRecord::Base
  belongs_to :user
  versioned
end


class Order < ActiveRecord::Base
   belongs_to :user

   def address
     @address ||= (user.address.revert_to(updated_at) and user.address)
   end
end

这篇关于如何使用 Ruby on Rails 中的映射表跟踪模型历史?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆