require 'spec_helper'

describe ShoppingCart do

  let(:user) { FactoryGirl.create(:user) }
  let(:jam_track) { FactoryGirl.create(:jam_track) }
  let(:jam_track2) { FactoryGirl.create(:jam_track) }
  let(:jam_track3) { FactoryGirl.create(:jam_track) }
  let(:jam_track4) { FactoryGirl.create(:jam_track) }
  let(:jam_track5) { FactoryGirl.create(:jam_track) }
  let(:jam_track6) { FactoryGirl.create(:jam_track) }
  let(:jam_track7) { FactoryGirl.create(:jam_track) }
  let(:gift_card) {FactoryGirl.create(:gift_card_type)}
  let(:gift_card2) {FactoryGirl.create(:gift_card_type)}

  before(:each) do
    ShoppingCart.delete_all
  end

  it "can reference a shopping cart" do
    shopping_cart = ShoppingCart.create user, jam_track, 1

    shopping_cart.errors.any?.should be_false
    shopping_cart.valid?.should be_true
    user.reload
    ShoppingCart.count.should == 1
    user.shopping_carts.count.should == 1
    user.shopping_carts[0].product_info[:name].should == jam_track.name
    user.shopping_carts[0].product_info[:price].should == jam_track.price
    user.shopping_carts[0].cart_type.should == jam_track.class::PRODUCT_TYPE
    user.shopping_carts[0].quantity.should == 1
  end

  it "allows mix of free and not free stuff" do
    cart1 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
    cart1.should_not be_nil
    cart1.errors.any?.should be_false
    user.reload
    cart2 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
    cart2.errors.any?.should be_false
    user.reload
    user.shopping_carts.length.should eq(1)
    cart3 = ShoppingCart.add_item_to_cart(user, gift_card)
    cart3.errors.any?.should be_false
    user.reload
    user.shopping_carts.length.should eq(2)
    cart4 = ShoppingCart.add_jam_track_to_cart(user, jam_track2)
    cart4.errors.any?.should be_false
    user.reload
    user.shopping_carts.length.should eq(3)
  end

  it "should not add duplicate JamTrack to ShoppingCart" do
    user.has_redeemable_jamtrack = false
    user.save!
    cart1 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
    cart1.should_not be_nil
    cart1.errors.any?.should be_false
    user.reload
    cart2 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
    cart2.errors.any?.should be_true
  end

  it "a second giftcard just adds quantity" do

  end

  describe "redeemable behavior" do

    it "removes redeemable item to shopping cart (maintains only one in cart)" do

      user.has_redeemable_jamtrack.should be_true
      cart1 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
      cart1.should_not be_nil
      cart1.errors.any?.should be_false
      cart1.marked_for_redeem.should eq(1)
      user.reload
      cart2 = ShoppingCart.add_jam_track_to_cart(user, jam_track2)
      cart2.should_not be_nil
      cart2.errors.any?.should be_false
      cart2.marked_for_redeem.should eq(1)

      ShoppingCart.find_by_id(cart1.id).should be nil


      ShoppingCart.remove_jam_track_from_cart(user, cart2)

      user.reload
      user.shopping_carts.length.should eq(0)
      ShoppingCart.find_by_id(cart2.id).should be nil
    end
  end

  describe "multiple free jamtracks" do

    before(:each) do
      user.gifted_jamtracks = 5
      user.save!
    end

    it "user can add and remove jamtracks without issue, until 'mixed' free/non-free is hit" do
      cart1 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
      cart1.should_not be_nil
      cart1.errors.any?.should be_false

      user.reload
      cart2 = ShoppingCart.add_jam_track_to_cart(user, jam_track2)
      cart2.errors.any?.should be_false
      user.reload
      user.shopping_carts.length.should eq(2)
      cart1.marked_for_redeem.should eq(1)
      cart2.marked_for_redeem.should eq(1)

      cart3 = ShoppingCart.add_jam_track_to_cart(user, jam_track3)
      cart3.errors.any?.should be_false
      user.reload
      user.shopping_carts.length.should eq(3)
      cart1.marked_for_redeem.should eq(1)
      cart2.marked_for_redeem.should eq(1)
      cart3.marked_for_redeem.should eq(1)

      cart4 = ShoppingCart.add_jam_track_to_cart(user, jam_track4)
      cart4.errors.any?.should be_false
      user.reload
      user.shopping_carts.length.should eq(4)
      cart1.marked_for_redeem.should eq(1)
      cart2.marked_for_redeem.should eq(1)
      cart3.marked_for_redeem.should eq(1)
      cart4.marked_for_redeem.should eq(1)

      cart5 = ShoppingCart.add_jam_track_to_cart(user, jam_track5)
      cart5.errors.any?.should be_false
      user.reload
      user.shopping_carts.length.should eq(5)
      cart1.marked_for_redeem.should eq(1)
      cart2.marked_for_redeem.should eq(1)
      cart3.marked_for_redeem.should eq(1)
      cart4.marked_for_redeem.should eq(1)
      cart5.marked_for_redeem.should eq(1)

      cart6 = ShoppingCart.add_jam_track_to_cart(user, jam_track6)
      cart6.errors.any?.should be_false
      user.reload
      user.shopping_carts.length.should eq(6)
      cart1.marked_for_redeem.should eq(1)
      cart2.marked_for_redeem.should eq(1)
      cart3.marked_for_redeem.should eq(1)
      cart4.marked_for_redeem.should eq(1)
      cart5.marked_for_redeem.should eq(1)
      cart6.marked_for_redeem.should eq(1)

      cart7 = ShoppingCart.add_jam_track_to_cart(user, jam_track7)
      cart7.errors.any?.should be_false
      user.reload
      user.shopping_carts.length.should eq(7)
      cart1.marked_for_redeem.should eq(1)
      cart2.marked_for_redeem.should eq(1)
      cart3.marked_for_redeem.should eq(1)
      cart4.marked_for_redeem.should eq(1)
      cart5.marked_for_redeem.should eq(1)
      cart6.marked_for_redeem.should eq(1)
    end
  end

  describe "gift cards" do
    it "can not add multiple of same type" do
      cart1 = ShoppingCart.add_item_to_cart(user, gift_card)
      cart1.should_not be_nil
      cart1.errors.any?.should be_false

      user.reload
      user.has_redeemable_jamtrack = true
      user.shopping_carts.length.should eq(1)
      user.shopping_carts[0].quantity.should eql(1)

      cart2 = ShoppingCart.add_item_to_cart(user, gift_card)
      cart2.should_not be_nil
      # it's the same type, so it's blocked
      cart2.errors.any?.should be_true
      cart2.errors[:cart_id].should eq(["has already been taken"])
    end
  end

  describe "mixed" do
    it "non-free then free" do
      jam_track.allow_free = false
      jam_track.save!

      # you shouldn't be able to add a free after a non-free
      user.has_redeemable_jamtrack = true
      user.save!

      cart1 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
      cart1.should_not be_nil
      cart1.errors.any?.should be_false

      user.reload
      cart2 = ShoppingCart.add_jam_track_to_cart(user, jam_track2)
      cart2.errors.any?.should be_false
      #cart2.errors[:base].should eq(["You can not add a free JamTrack to a cart with non-free items.  Please clear out your cart."])

      user.reload
      user.shopping_carts.length.should eq(2)
    end

    it "free then non-free" do

      jam_track2.allow_free = false
      jam_track2.save!
      cart1 = ShoppingCart.add_jam_track_to_cart(user, jam_track)
      cart1.should_not be_nil
      cart1.errors.any?.should be_false

      user.reload

      cart2 = ShoppingCart.add_jam_track_to_cart(user, jam_track2)
      cart2.errors.any?.should be_false
      #cart2.errors[:base].should eq(["You can not add a non-free JamTrack to a cart containing free items.  Please clear out your cart."])

      user.reload
      user.shopping_carts.length.should eq(2)
    end
  end
end
