Intro: I started working three month ago and i have never used JavaScript before, i don't know what is the best practice in JS and i feel like my code can be improved a lot, so i'm here searching for tips and tricks or other infos who can make my code better.
Task: Take in input a dictionary with all opening time of a shop and return a formatted string.
Input: A dictionary with seven pairs, the key is "openingMon" .. "openingSun".
Time separated with dash "-" it's the opening time, if there is a ";" in that time is closed.
Note that the input is always a dictionary and always have this keys.
openings = {
"openingMon" : "08:00 - 12:00 ; 13:00 - 21:00",
"openingTue" : "08:00 - 10:00 ; 16:00 - 20:00",
"openingWed" : "10:00 - 10:00 ; 16:00 - 20:00",
"openingThu" : "08:00 - 14:00 ",
"openingFri" : "08:00 - 20:00",
"openingSat" : "",
"openingSun" : ""
}
Output: a formatted string with the following rule:
- If all value is empty you must return "Missing opening time".
- If the value corresponding to the current day of the week is not empty you must return if the shop is open or closed and the closing/opening time.
- If the value corresponding to the current day of the week is empty but at least another value is not empty you must return that the shop is closed and the opening time of the next day of the week with not empty value.
- If tomorrow's value is empty you must include the name of the next day with opening time.
- If the shop is closed for the rest of the day you must return a string like if the current day's value it's empty.
Examples (for the given input):
- If it's Sunday return "Closed today - Opening: Tomorrow 08:00".
- If it's Saturday return "Closed today - Opening: Monday 08:00".
- If it's Thursday and it's 09:00 return "Open now - Closing: 14:00".
- If it's Tuesday and it's 11:00 return "Closed now - Opening: 16:00".
- If it's Tuesday and it's 21:00 return "Closed today - Opening: Tomorrow 10:00".
- If it's Friday and it's 21:00 return "Closed today - Opening: Monday 08:00".
Solution:
// Set the string with the opening information
function set_opening(opening_dict) {
// Convert from a time string to an int: "08:36" -> 836
let toInt = (x) => parseInt(x.replace(":", ""));
// For using a string of opening time like a list: i = 2, o = "08:30 - 13:00 ; 15:00 - 20:00" -> "15:00"
let toList = (i, o = opening) => o == "" ? o : (o.includes(";") ? (o.split(" ; ")[Math.floor(i / 2)]).split(" - ")[i % 2] : o.split(" - ")[i]);
// Get opening time based on a day of the week: 2 -> "08:30 - 13:00 ; 15:00 - 20:00"
let getOpening = (x) => opening_dict["opening" + week_days[x].slice(0, 3)];
// Get last closing time from a string: "08:30 - 13:00 ; 15:00 - 20:00" -> 2000
let getClose = (o = opening) => o == "" ? 0 : o.includes(";") ? toInt(toList(3, o)) : toInt(toList(1, o));
// Get opening time from opening as an int: i = 2, o = "08:30 - 13:00 ; 15:00 - 20:00" -> 1500
let getTime = (i, o = opening) => o == "" ? 0 : toInt(toList(i, o));
// Check if all value is empty
let is_empty = true;
for (const value of Object.values(opening_dict)) {
is_empty = is_empty && value == "";
}
// If all value is empty there is no openings
if (is_empty) {
return "Missing opening time";
}
let week_days = ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"];
let now = new Date(Date.now());
// Save current time as an int
let time_now = now.getHours() + (now.getMinutes() > 9 ? "" : "0") + now.getMinutes();
// Save the opening time for today (getDay return 0 for sunday and 6 for saturday)
let opening = getOpening(now.getDay());
// If today is closed tell next opening day
if (opening == "" || time_now >= getClose()) {
let next_opening_day = now.getDay() + 1;
// Save next opening day
while (next_opening_day != now.getDay()) {
if (getOpening(next_opening_day) != "") {
break;
}
// If it's sunday go to monday
next_opening_day = (next_opening_day + 1) % 7;
}
let next_opening = next_opening_day == now.getDay() + 1 ? "Tomorrow" : week_days[next_opening_day];
return `Closed today - Opening: ${next_opening} ${toList(0, getOpening(next_opening_day))}`;
}
// Check current time and say if it's is open or closed, along with next opening/closing time
if (time_now < getTime(0)) {
return `Closed now - Opening: ${toList(0)}`;
} else if (getTime(0) <= time_now && time_now < getTime(1)) {
return `Open now - Closing: ${toList(1)}`;
}
// If current openings have four time
if (time_now < getTime(2)) {
return `Closed now - Opening: ${toList(2)}`;
} else if (getTime(2) <= time_now && time_now < getTime(3)) {
return `Open now - Closing: ${toList(3)}`;
}
};
let getClose = (o = opening) => o == "" ? 0 : o.includes(";") ? toInt(toList(3, o)) : toInt(toList(1, o));
TypeError: Cannot read property 'includes' of undefined
\$\endgroup\$set_opening
? \$\endgroup\$