Users can sell items and add an expiration date that varies from 1-3 weeks out from current date.
This is how I store the expiration date as a Double
. Do I need to be explicit about other date components like year, month, etc?
enum Weeks: Int {
case one
case two
case three
}
extension Weeks {
var timeInterval: Double? {
let currentDate = Date()
let calendar = Calendar.current
let calendarComponents: Set<Calendar.Component> = Set(arrayLiteral: Calendar.Component.year, Calendar.Component.month, Calendar.Component.day, Calendar.Component.hour, Calendar.Component.minute, Calendar.Component.second)
var components = calendar.dateComponents(calendarComponents, from: currentDate)
switch self {
case .one: components.weekOfMonth = 1
case .two: components.weekOfMonth = 2
case .three: components.weekOfMonth = 3
}
if let expirationDate = calendar.date(from: components) {
return expirationDate.timeIntervalSince1970 as Double
} else {
return nil
}
}
}
This is how I calculate the countdown in Date
extension:
func countdown(to date: Date) -> CountdownResponse {
let difference = Calendar.current.dateComponents([.day, .hour, .minute, .second], from: self, to: date)
guard let day = difference.day, let hour = difference.hour, let minute = difference.minute, let second = difference.second else {
return .error(message: "One or more date components are nil.")
}
if day <= 0 && hour <= 0 && minute <= 0 && second <= 0 {
return .isFinished
}
let days = displayableText(from: difference.day)
let hours = displayableText(from: difference.hour)
let minutes = displayableText(from: difference.minute)
let seconds = displayableText(from: difference.second)
let timeRemaining = "\(days) : \(hours) : \(minutes) : \(seconds)"
return .result(time: timeRemaining)
}
This is how I'd like to get the countdown, and then I check the response enum for error, or result. But this gives me incorrect time.
let expirationDate = Date(timeIntervalSince1970: self.item.expirationDate)
let response = currentDate.countdown(to: expirationDate)
When I create date manually and test like below, it works as expected.
var comp = calendar.dateComponents(calendarComponents, from: Date())
comp.year = 2017
comp.month = 8
comp.day = 24
comp.minute = 50
comp.second = 30
What am I doing wrong? Am I persisting date as time interval incorrectly, or creating date from timeInterval incorrectly?
As I look over the code I realize that I may be calculating the week wrong. If it's the second week of the month and a user chooses for item to expire in 3 weeks, week of month shouldn't be 3, it needs to be 3 weeks from current week of month. Any guidance on how to fix this logic is appreciated.