-
Notifications
You must be signed in to change notification settings - Fork 45
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Amy Cash - Pipes - Hotel #33
base: master
Are you sure you want to change the base?
Conversation
HotelWhat We're Looking For
Good work overall. The big thing I notice missing is test coverage around checking which rooms are reserved when. The logic is quite complex and it's also hidden within other functionality, which makes it difficult to test explicitly. This sort of scenario is where design work starts to pay off - by isolating behaviors like comparing two date ranges, you can test them without all the overhead of hotels and reservations, as the foundational units of your application. For an example of how design can make testing easier, you should check out our reference implementation. That being said, I'm pretty happy with what you've submitted. Your design is clear and intentional, and your code is well-organized and easy to read. Keep up the good work! |
|
||
def self.check_dates(first, last) | ||
if Date.parse(first) > Date.parse(last) | ||
raise ArgumentError, "Check Out Date is earlier than Check in Date" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is it valid if first == last
?
|
||
class DateRange | ||
|
||
attr_reader :check_in, :check_out, :date_range |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You never instantiate this class! You're basically using it as a library of methods to work with dates, which means it might be clearer as a module.
|
||
def make_reservation(id, day_in, day_out, discount: 0, block_name: nil, room: 0) | ||
available = open_rooms(day_in, day_out) | ||
if room == 0 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since room number is an integer, it might make more sense to use a non-integer sentinel value here. nil
is usually a good choice.
lib/hotel.rb
Outdated
DateRange.check_dates(day_in, day_out) | ||
DateRange.create_range(day_in, day_out).each do |date| | ||
found_reservations << all_reservations.find_all { |reservation| reservation.nights_reserved.include?(Date.parse(date)) } | ||
end #each date |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is an example of tight coupling between Hotel
and Reservation
. Peeking into reservation.nights_reserved
means that if that implementation ever changes, this code will need to change too. Instead, it might be cleaner to write a method Reservation#includes_date
, and call it here.
if reservation.id == reservation_id | ||
return reservation.total_cost | ||
else | ||
return "Reservation Not Found" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This would be a good place to raise an error. Maybe a custom NoSuchReservationError
?
elsif room != 0 && available.include?(room) | ||
first_open = room | ||
else | ||
raise ArgumentError, "Requested Room is Not Available during Date Range" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure an ArgumentError
is the right call here. That usually indicates the arguments are invalid (i.e. a bogus room number or date range) or not of the right type, but that's not what this error is describing. Maybe this would be a good place to use a custom exception.
describe "DateRange Class" do | ||
before do | ||
@date_test = Hotel::DateRange.new | ||
end #before |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You don't have any tests around check_dates
!
@hotel.make_reservation(2224, "2012/12/13", "2012/12/17") | ||
@hotel.open_rooms("2012/12/12", "2012/12/13").must_be_kind_of Array | ||
@hotel.open_rooms("2012/12/12", "2012/12/13")[0].must_equal 3 | ||
end #open rooms |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Other cases I'd be interested in:
- What if there are no reservations? (it should return an empty array)
- Do reservations that don't overlap the date range affect the list? (they shouldn't)
- Check the boundaries of what counts as an overlap. What about a reservation that ends on the checkin date, or starts on the checkout date?
proc { | ||
@hotel.make_reservation(1000, "2001/1/30", "2001/2/4", room: 1) | ||
}.must_raise ArgumentError | ||
end |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a good start, but I'd like to see more coverage around what date ranges will conflict with each other. Cases I'd be interested in:
- Not available:
- Same dates
- Overlaps in the front
- Overlaps in the back
- Completely contained
- Completely containing
- Available:
- Completely before
- Completely after
- Ends on the checkin date
- Starts on the checkout date
|
||
describe "Blocks" do | ||
|
||
it "Can call Block to create an array to store block information" do |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Test coverage looks pretty good around blocks. There are just a couple of places where it seems like things are missing:
- What happens if you try to create a block when there are not enough rooms available?
- What if the dates on the reservation don't match those on the block?
Hotel
Congratulations! You're submitting your assignment!
Comprehension Questions