1

テストが失敗する理由を見つけるのに苦労しています:

describe User, "Instance Methods" do
  describe "leave_group!" do
    it "should set group_id to nil" do
      @user = Factory(:user)
      @group_2 = Factory(:group, :owner => @user)

      @user.leave_group!
      @user.reload.group_id.should be_nil # THIS LINE IS FAILING!!!
    end

    it "should assign another owner to group, if owner was user" do
      @user = Factory(:user)
      @group = Factory(:group, :owner => @user)
      1.upto(4) { @group.add_user Factory(:user) }

      @user.leave_group!
      @group.reload.owner.should_not eql(@user)
    end
  end
end

これらは私が使用しているモデルです:

class User < ActiveRecord::Base
  # Associations
  has_one :own_group, :class_name => "Group", :foreign_key => "owner_id"
  belongs_to :group

  def leave_group!
    current_group_id, current_group_owner = self.group.id, self.group.owner
    self.group_id = nil
    save!
    Group.find(current_group_id).randomize_owner! if current_group_owner == self
  end
end

class Group < ActiveRecord::Base
  # Associations
  has_many :users
  belongs_to :owner, class_name: "User"

  def randomize_owner!
    current_users = self.users
    return false unless current_users.length > 1
    begin
      new_user = current_users.sort_by { rand }.first
    end while self.owner == new_user
    self.owner_id = new_user.id
    save!
  end
end

ここで何か間違ったことをしていますか?改善できますか?さらに重要なことに、その 1 つのテストが失敗するのはなぜでしょうか?

その単一のテストを実行した場合のログ出力は次のとおりです。

SQL (0.2ms)   SELECT name
FROM sqlite_master
WHERE type = 'table' AND NOT name = 'sqlite_sequence'

AREL (0.3ms)  INSERT INTO "users" ("name", "uid", "provider", "email", "image_url", "group_id", "created_at", "updated_at", "timezone", "public_readings", "is_visible_on_leaderboards", "phone_number") VALUES ('John Doe', '314159265', 'facebook', 'john@does.com', NULL, NULL, '2011-07-18 02:02:08.455229', '2011-07-18 02:02:08.455229', NULL, 't', 't', NULL)
Group Load (0.1ms)  SELECT "groups".* FROM "groups" WHERE "groups"."key" = 'SNYEMJ' LIMIT 1
AREL (0.1ms)  INSERT INTO "groups" ("name", "key", "score", "owner_id", "created_at", "updated_at") VALUES ('John''s Group', 'SNYEMJ', 0, 1, '2011-07-18 02:02:08.522442', '2011-07-18 02:02:08.522442')
AREL (0.0ms)  UPDATE "users" SET "group_id" = 1, "updated_at" = '2011-07-18 02:02:08.524342' WHERE "users"."id" = 1
Group Load (0.1ms)  SELECT "groups".* FROM "groups" WHERE "groups"."id" = 1 LIMIT 1
User Load (0.2ms)  SELECT "users".* FROM "users" WHERE ("users".group_id = 1)
User Load (0.2ms)  SELECT "users".* FROM "users" WHERE "users"."id" = 1 LIMIT 1

最後の 3 行はすべて選択です。レールはユーザーから group_id を削除しようとさえしていないことに注意してください。(テスト ユーザー用に 1 つ、テスト グループ用に 1 つ、テスト ユーザーに group_id を割り当てる 1 つの更新の 2 つの挿入があります)。

4

2 に答える 2

1

テストの@user.reload前に呼び出しを追加してみてください。@user.leave_group

ファクトリから作成すると、ユーザー レコードは DB 内のグループで更新されますが、オブジェクトはそうではない@group_2と思われます。次に、nil のa を使用して@user呼び出すleave_group!と、オブジェクトが変更されないため、保存は何も実行されません。次に、テストの次の行で、以前に割り当てられた DB からのをリロードします。@usergroup ID@usergroup_id

于 2011-07-18T08:27:16.377 に答える
0

次のようにモデルクラスを試してみてください:

class User < ActiveRecord::Base
  # Associations
  has_one :own_group, :class_name => "Group", :foreign_key => "owner_id"
  belongs_to :group

  def leave_group!
    group_randomize_owner
    self.group.clear
  end

  private

  def group_randomize_owner
    if group.owner == self
      group.randomize_owner!
    end
  end
end
于 2011-07-17T14:33:05.263 に答える