class CreateGroups < ActiveRecord::Migration def self.up create_table :parties do |t| t.column :type, :string end create_table :groups, :primary_key => :party_id do |t| t.string :name, :null => false end rename_column :users, :id, :party_id execute "INSERT INTO parties (id, type) SELECT party_id, 'User' FROM users" if ActiveRecord::Base.connection.adapter_name.downcase == "postgresql" ActiveRecord::Base.connection.execute "select setval('parties_id_seq', (select max(id) from parties));" end add_foreign_key :users, :party_id, :parties, :id create_table :groups_users, :id => false do |t| t.integer :group_id, :null => false, :references => nil t.integer :user_id, :null => false, :references => nil end add_foreign_key :groups_users, :group_id, :groups, :party_id add_foreign_key :groups_users, :user_id, :users, :party_id add_index :groups_users, ["group_id", "user_id"], :unique => true add_column :periods, :party_id, :integer add_index :periods, ["party_id", "position"], :unique => true add_column :tasks, :backlog_id, :integer load_classes Backlog.find(:all).each do |b| next if b.periods.empty? group = Group.create! :name => (b.name + 'Group') b.periods.each do |p| p.party_id = group.id p.save! p.tasks.each {|t| t.backlog = b; t.save!} end users = b.periods.map {|p| p.tasks.map {|t| t.estimates.map{|e| e.user} + t.works.map{|w| w.user}}}.flatten.compact.uniq users.each do |u| execute "INSERT INTO groups_users (group_id, user_id) VALUES (#{group.id}, #{u.id})" end end remove_column :periods, :backlog_id end def self.down add_column :periods, :backlog_id, :integer load_classes Period.find(:all).each do |p| if first_task = p.tasks.first p.backlog_id = first_task.backlog_id p.save! end end change_column :periods, :backlog_id, :integer, :null => false remove_column :tasks, :backlog_id remove_column :periods, :party_id drop_table :groups_users rename_column :users, :party_id, :id drop_table :groups drop_table :parties end def self.load_classes class_eval < 'CreateGroups::User' # has_many :users, :through => :groups_users, :class_name => 'CreateGroups::User' end class Backlog < ActiveRecord::Base has_many :periods end class Period < ActiveRecord::Base # belongs_to :backlog # belongs_to :party has_many :tasks end class Estimate < ActiveRecord::Base belongs_to :user end class Work < ActiveRecord::Base belongs_to :user end class Task < ActiveRecord::Base belongs_to :backlog belongs_to :period has_many :estimates has_many :works end EOF end end