Validate that tracks don't overlap
Also, add scope for accepted tracks
This commit is contained in:
parent
16f294f3e8
commit
7067803cb9
2 changed files with 106 additions and 0 deletions
|
|
@ -31,9 +31,11 @@ class Track < ActiveRecord::Base
|
||||||
validates :description, presence: true, if: :self_organized?
|
validates :description, presence: true, if: :self_organized?
|
||||||
validate :valid_dates
|
validate :valid_dates
|
||||||
validate :valid_room, if: :self_organized_and_accepted_or_confirmed?
|
validate :valid_room, if: :self_organized_and_accepted_or_confirmed?
|
||||||
|
validate :overlapping
|
||||||
|
|
||||||
before_validation :capitalize_color
|
before_validation :capitalize_color
|
||||||
|
|
||||||
|
scope :accepted, -> { where(state: 'accepted') }
|
||||||
scope :confirmed, -> { where(state: 'confirmed') }
|
scope :confirmed, -> { where(state: 'confirmed') }
|
||||||
scope :cfp_active, -> { where(cfp_active: true) }
|
scope :cfp_active, -> { where(cfp_active: true) }
|
||||||
|
|
||||||
|
|
@ -209,4 +211,20 @@ class Track < ActiveRecord::Base
|
||||||
errors.add(:room, "must be a room of #{program.conference.venue.name}")
|
errors.add(:room, "must be a room of #{program.conference.venue.name}")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
##
|
||||||
|
# Check that there is no other track in the same room with overlapping dates
|
||||||
|
def overlapping
|
||||||
|
return unless start_date && end_date && room && program.try(:tracks)
|
||||||
|
(program.tracks.accepted + program.tracks.confirmed - [self]).each do |other_track|
|
||||||
|
if other_track.room == room &&
|
||||||
|
other_track.start_date && other_track.end_date &&
|
||||||
|
(other_track.start_date <= start_date && other_track.end_date >= start_date ||
|
||||||
|
other_track.start_date <= end_date && other_track.end_date >= end_date ||
|
||||||
|
start_date <= other_track.start_date && other_track.end_date <= end_date)
|
||||||
|
errors.add(:track, 'has overlapping dates with a confirmed or accepted track in the same room')
|
||||||
|
break
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
|
||||||
|
|
@ -136,9 +136,97 @@ describe Track do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
describe '#overlapping' do
|
||||||
|
before :each do
|
||||||
|
@conference = create(:conference, start_date: Date.current - 1.day, end_date: Date.current + 2.days)
|
||||||
|
@conference.venue = create(:venue)
|
||||||
|
@room = create(:room, venue: @conference.venue)
|
||||||
|
end
|
||||||
|
|
||||||
|
context 'is valid' do
|
||||||
|
it 'when the tracks are in different rooms' do
|
||||||
|
other_room = create(:room, venue: @conference.venue)
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: other_room, start_date: Date.current, end_date: Date.current)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current)
|
||||||
|
expect(track.valid?).to eq true
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'when it ends before the other tracks' do
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current - 1.day, end_date: Date.current - 1.day)
|
||||||
|
expect(track.valid?).to eq true
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'when it starts after the other tracks' do
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current + 1.day, end_date: Date.current + 1.day)
|
||||||
|
expect(track.valid?).to eq true
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
context 'is invalid' do
|
||||||
|
it 'when it starts or ends with another track in the same room' do
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current)
|
||||||
|
expect(track.valid?).to eq false
|
||||||
|
expect(track.errors[:track]).to eq ['has overlapping dates with a confirmed or accepted track in the same room']
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'when it starts before another track and ends after the other starts and before it ends' do
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current + 2.days)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current - 1.day, end_date: Date.current + 1.day)
|
||||||
|
expect(track.valid?).to eq false
|
||||||
|
expect(track.errors[:track]).to eq ['has overlapping dates with a confirmed or accepted track in the same room']
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'when it starts after another track and before it ends and ends after the other' do
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current + 2.days)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current + 1.day, end_date: Date.current + 3.days)
|
||||||
|
expect(track.valid?).to eq false
|
||||||
|
expect(track.errors[:track]).to eq ['has overlapping dates with a confirmed or accepted track in the same room']
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'when it starts after another track and ends before the other' do
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current + 2.days)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current + 1.day, end_date: Date.current + 1.day)
|
||||||
|
expect(track.valid?).to eq false
|
||||||
|
expect(track.errors[:track]).to eq ['has overlapping dates with a confirmed or accepted track in the same room']
|
||||||
|
end
|
||||||
|
|
||||||
|
it 'when it starts before another track and ends after the other' do
|
||||||
|
create(:track, :self_organized, state: 'confirmed', program: @conference.program, room: @room, start_date: Date.current, end_date: Date.current)
|
||||||
|
track = build(:track, :self_organized, program: @conference.program, room: @room, start_date: Date.current - 1.day, end_date: Date.current + 1.day)
|
||||||
|
expect(track.valid?).to eq false
|
||||||
|
expect(track.errors[:track]).to eq ['has overlapping dates with a confirmed or accepted track in the same room']
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe 'scope' do
|
describe 'scope' do
|
||||||
|
describe '#accepted' do
|
||||||
|
before :each do
|
||||||
|
@program = create(:program)
|
||||||
|
end
|
||||||
|
|
||||||
|
context 'includes' do
|
||||||
|
it 'when track is accepted' do
|
||||||
|
accepted_track = create(:track, state: 'accepted', program: @program)
|
||||||
|
expect(@program.tracks.accepted.include?(accepted_track)).to eq true
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
context 'excludes' do
|
||||||
|
%w[new to_accept confirmed to_reject rejected canceled withdrawn].each do |state|
|
||||||
|
it "when track is #{state.humanize}" do
|
||||||
|
not_accepted_track = create(:track, state: state, program: @program)
|
||||||
|
expect(@program.tracks.accepted.include?(not_accepted_track)).to eq false
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
describe '#confirmed' do
|
describe '#confirmed' do
|
||||||
before :each do
|
before :each do
|
||||||
@program = create(:program)
|
@program = create(:program)
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue