jam-cloud/ruby/spec/jam_ruby/models/user_sync_spec.rb

543 lines
20 KiB
Ruby

require 'spec_helper'
describe UserSync do
let(:user1) {FactoryGirl.create(:user)}
let(:user2) {FactoryGirl.create(:user)}
before(:each) do
end
it "empty results" do
UserSync.all.length.should == 0
end
describe "index" do
it "empty results" do
data = UserSync.index({user_id: user1})
data[:query].length.should == 0
data[:next].should be_nil
end
describe "backing_tracks" do
let!(:recording1) {
recording = FactoryGirl.create(:recording, owner: user1, band: nil, duration:1)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: recording.owner, fully_uploaded:false)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: user2, fully_uploaded:false)
recording.recorded_backing_tracks << FactoryGirl.create(:recorded_backing_track, recording: recording, user: recording.owner, fully_uploaded:false)
recording.save!
recording.reload
recording
}
let(:sorted_tracks) {
Array.new(recording1.recorded_tracks).sort! {|a, b|
if a.created_at == b.created_at
a.id <=> b.id
else
a.created_at <=> b.created_at
end
}
}
# backing tracks should only list download, or upload, for the person who opened it, for legal reasons
it "lists backing track for opener" do
data = UserSync.index({user_id: user1.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.count.should eq(3)
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
user_syncs[2].recorded_backing_track.should == recording1.recorded_backing_tracks[0]
end
it "does not list backing track for non-opener" do
data = UserSync.index({user_id: user2.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.count.should eq(2)
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
end
end
it "one mix and quick mix" do
mix = FactoryGirl.create(:mix)
mix.recording.duration = 1
mix.recording.save!
quick_mix = FactoryGirl.create(:quick_mix_completed, recording:mix.recording, user: mix.recording.recorded_tracks[0].user, autowire:false)
data = UserSync.index({user_id: mix.recording.recorded_tracks[0].user.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 3
user_syncs[0].recorded_track.should == mix.recording.recorded_tracks[0]
user_syncs[0].mix.should be_nil
user_syncs[0].quick_mix.should be_nil
user_syncs[1].mix.should == mix
user_syncs[1].recorded_track.should be_nil
user_syncs[1].quick_mix.should be_nil
user_syncs[2].mix.should be_nil
user_syncs[2].recorded_track.should be_nil
user_syncs[2].quick_mix.should eq(quick_mix)
end
# https://jamkazam.atlassian.net/browse/VRFS-2450
it "no longer returned after fully uploaded and unclaimed" do
mix = FactoryGirl.create(:mix)
mix.recording.duration = 1
mix.recording.save!
quick_mix = FactoryGirl.create(:quick_mix_completed, recording:mix.recording, user: mix.recording.recorded_tracks[0].user, autowire:false, fully_uploaded: true)
mix.recording.recorded_tracks[0].fully_uploaded = true
mix.recording.recorded_tracks[0].save!
mix.recording.claimed_recordings[0].discarded = true
mix.recording.claimed_recordings[0].save!
data = UserSync.index({user_id: mix.recording.recorded_tracks[0].user.id})
user_syncs = data[:query]
user_syncs.length.should == 0
end
it "two mixes, one not belonging to querier" do
mix1 = FactoryGirl.create(:mix)
mix2 = FactoryGirl.create(:mix)
mix1.recording.duration = 1
mix1.recording.save!
mix2.recording.duration = 1
mix2.recording.save!
data = UserSync.index({user_id: mix1.recording.recorded_tracks[0].user.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == mix1.recording.recorded_tracks[0]
user_syncs[0].mix.should be_nil
user_syncs[1].mix.should == mix1
user_syncs[1].recorded_track.should be_nil
data = UserSync.index({user_id: mix2.recording.recorded_tracks[0].user.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == mix2.recording.recorded_tracks[0]
user_syncs[0].mix.should be_nil
user_syncs[1].mix.should == mix2
user_syncs[1].recorded_track.should be_nil
end
describe "one recording with two users" do
let!(:recording1) {
recording = FactoryGirl.create(:recording, owner: user1, band: nil, duration:1)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: recording.owner, fully_uploaded:false)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: user2, fully_uploaded:false)
recording.save!
recording.reload
recording
}
let(:sorted_tracks) {
Array.new(recording1.recorded_tracks).sort! {|a, b|
if a.created_at == b.created_at
a.id <=> b.id
else
a.created_at <=> b.created_at
end
}
}
it "no claimed_recordings" do
# both user1 and user2 should be told about each others tracks, because both will need to upload their tracks
data = UserSync.index({user_id: user1.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
data = UserSync.index({user_id: user2.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
end
it "recording isn't over" do
recording1.duration = nil
recording1.save!
# nothing should be returned, because the recording isn't over
data = UserSync.index({user_id: user1.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 0
data = UserSync.index({user_id: user2.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 0
end
it "one user decides to keep the recording" do
claimed_recording = FactoryGirl.create(:claimed_recording, user: user1, recording: recording1, discarded:false)
claimed_recording.recording.should == recording1
data = UserSync.index({user_id: user1.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
data = UserSync.index({user_id: user2.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
end
it "one user decides to discard the recording" do
FactoryGirl.create(:claimed_recording, user: user1, recording: recording1, discarded:true)
data = UserSync.index({user_id: user1.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
data = UserSync.index({user_id: user2.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
end
it "both users decide to discard the recording" do
recording1.all_discarded = true
recording1.save!
data = UserSync.index({user_id: user1.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 0
data = UserSync.index({user_id: user2.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 0
end
end
describe "one recording with multi-track users" do
let!(:recording1) {
recording = FactoryGirl.create(:recording, owner: user1, band: nil, duration:1)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: recording.owner, fully_uploaded:false)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: recording.owner, fully_uploaded:false)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: user2, fully_uploaded:false)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: user2, fully_uploaded:false)
recording.save!
recording.reload
recording
}
let(:sorted_tracks) {
Array.new(recording1.recorded_tracks).sort! {|a, b|
if a.created_at == b.created_at
a.id <=> b.id
else
a.created_at <=> b.created_at
end
}
}
it "one user decides to keep the recording" do
claimed_recording = FactoryGirl.create(:claimed_recording, user: user1, recording: recording1, discarded:false)
claimed_recording.recording.should == recording1
data = UserSync.index({user_id: user1.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 4
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
user_syncs[2].recorded_track.should == sorted_tracks[2]
user_syncs[3].recorded_track.should == sorted_tracks[3]
data = UserSync.index({user_id: user2.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 4
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
user_syncs[2].recorded_track.should == sorted_tracks[2]
user_syncs[3].recorded_track.should == sorted_tracks[3]
end
end
end
describe "pagination" do
let!(:recording1) {
recording = FactoryGirl.create(:recording, owner: user1, band: nil, duration:1)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: recording.owner)
recording.recorded_tracks << FactoryGirl.create(:recorded_track, recording: recording, user: user2)
claimed_recording = FactoryGirl.create(:claimed_recording, user: recording.owner, recording: recording, discarded:false)
recording.save!
recording.reload
recording
}
let(:sorted_tracks) {
Array.new(recording1.recorded_tracks).sort! {|a, b|
if a.created_at == b.created_at
a.id <=> b.id
else
a.created_at <=> b.created_at
end
}
}
it "tiny page size" do
# get the 1st track
data = UserSync.index({user_id: user1.id, offset: 0, limit: 1})
data[:next].should == 1
user_syncs = data[:query]
user_syncs.length.should == 1
user_syncs[0].recorded_track.should == sorted_tracks[0]
data[:query].total_entries.should == 2
# then get the second track, which happens to be on an edge, pagination wise
data = UserSync.index({user_id: user1.id, offset: 1, limit: 1})
data[:next].should == 2
user_syncs = data[:query]
user_syncs.length.should == 1
user_syncs[0].recorded_track.should == sorted_tracks[1]
data[:query].total_entries.should == 2
# so prove it's on the edge by asking for 2 items instead of 1.
data = UserSync.index({user_id: user1.id, offset: 0, limit: 3})
data[:next].should == nil
user_syncs = data[:query]
user_syncs.length.should == 2
user_syncs[0].recorded_track.should == sorted_tracks[0]
user_syncs[1].recorded_track.should == sorted_tracks[1]
data[:query].total_entries.should == 2
data = UserSync.index({user_id: user1.id, offset: 2, limit: 1})
data[:next].should == nil
user_syncs = data[:query]
user_syncs.length.should == 0
data[:query].total_entries.should == 2
end
end
it "does not return deleted recordings" do
mix = FactoryGirl.create(:mix)
mix.recording.duration = 1
mix.recording.save!
quick_mix = FactoryGirl.create(:quick_mix_completed, recording:mix.recording, user: mix.recording.recorded_tracks[0].user, autowire:false)
mix.recording.mark_delete
data = UserSync.index({user_id: mix.recording.recorded_tracks[0].user.id})
data[:next].should be_nil
user_syncs = data[:query]
user_syncs.length.should == 0
end
describe "deletable" do
describe "one mix and one quick mix" do
let!(:mix) { m = FactoryGirl.create(:mix); m.recording.duration = 1; m.recording.save!; m}
let!(:quick_mix) { FactoryGirl.create(:quick_mix_completed, recording:mix.recording, user: mix.recording.recorded_tracks[0].user, autowire:false) }
it "unknown id" do
recording_ids = ['1']
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq(recording_ids)
end
it "unknown ids" do
recording_ids = ['1', '2', '3']
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq(recording_ids)
end
it "valid recording id" do
recording_ids = [mix.recording.id]
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq([])
end
it "valid recording id" do
recording_ids = [mix.recording.id]
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq([])
end
it "valid recording_id mixed with unknown ids" do
recording_ids = [mix.recording.id, '1']
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq(['1'])
end
it "null recording_ids allowed" do
# observed that the client can send null for recording_ids
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: nil)
result.should eq([])
end
end
describe "two recordings" do
let!(:mix) { m = FactoryGirl.create(:mix); m.recording.duration = 1; m.recording.save!; m}
let!(:quick_mix) { FactoryGirl.create(:quick_mix_completed, recording:mix.recording, user: mix.recording.recorded_tracks[0].user, autowire:false) }
let!(:mix2) { m = FactoryGirl.create(:mix); m.recording.duration = 1; m.recording.save!; m}
let!(:quick_mix2) { FactoryGirl.create(:quick_mix_completed, recording:mix2.recording, user: mix2.recording.recorded_tracks[0].user, autowire:false) }
before(:each) do
# fix up the user associated with the second mix/recording to be same as 1st
mix2.recording.owner = mix.recording.owner
mix2.recording.save!
mix2.recording.recorded_tracks[0].user = mix.recording.owner
mix2.recording.recorded_tracks[0].save!
end
it "unknown id" do
recording_ids = ['1']
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq(recording_ids)
end
it "unknown ids" do
recording_ids = ['1', '2', '3']
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq(recording_ids)
end
it "valid recording id" do
recording_ids = [mix.recording.id, mix2.recording.id]
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq([])
end
it "valid recording id" do
recording_ids = [mix.recording.id]
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq([])
end
it "valid recording_id mixed with unknown ids" do
recording_ids = [mix.recording.id, '1']
result = UserSync.deletables(user_id: mix.recording.recorded_tracks[0].user.id, recording_ids: recording_ids)
result.should eq(['1'])
end
end
it "resolved recordings" do
# start with a recording with a fully uploaded recorded_track, and no claim
recording = FactoryGirl.create(:recording_with_track, owner: user1)
recording.duration = 1
recording.save!
recording_ids = [recording.id]
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq(recording_ids)
# set the recorded_track to not fully uploaded, which should make it not deletable
recording.recorded_tracks[0].fully_uploaded = false
recording.recorded_tracks[0].save!
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq([])
# mark recording as deleted, which should make it deletable
recording.deleted = true
recording.save!
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq(recording_ids)
# mark recording as fully discarded, which should make it deletable
recording.all_discarded = true
recording.deleted = false
recording.save!
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq(recording_ids)
# claim the recording, and make the track not fully uploaded
recording.recorded_tracks[0].fully_uploaded = false
recording.all_discarded = false
claim = FactoryGirl.create(:claimed_recording, user: user1, recording: recording)
recording.save!
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq([])
# create a mix while still claiming the recording
mix = FactoryGirl.create(:mix, autowire:false, recording:recording)
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq([])
# now take away the claim, and make sure the track is fully uploaded
claim.discarded = true
claim.save!
# without a claimed recording, make the track fully uploaded, so as to not trigger 'need to upload' logic
recording.recorded_tracks[0].fully_uploaded = true
recording.recorded_tracks[0].save!
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq(recording_ids)
# if we make a quick mix, but still have no claim, we still should still need to delete the recording
quick_mix = FactoryGirl.create(:quick_mix, autowire:false, user: user1, recording: recording, fully_uploaded: true)
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq(recording_ids)
# make the quick_mix be not fully_uploaded, which should make it not be marked for deleting because we need to upload it
quick_mix.fully_uploaded = false
quick_mix.save!
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq([])
quick_mix.fully_uploaded = true
quick_mix.save!
claim.discarded = false
claim.save!
result = UserSync.deletables(user_id: user1.id, recording_ids: recording_ids)
result.should eq([])
end
end
end