1 var flask = "{{ url_for('hello', _external=True) }}"
5 var updateRemote = undefined; // defined iff remote server accessible
6 var timeToLogout = undefined; // defined during logout countdown
8 var reloadTimer = undefined;
9 var id_user; // ID of the user who is to be accounted for the next coffee
10 var identifier_registration = false; // true if identifier is supposed to be registered for user
11 var eventMsg = undefined; // Feedback message about the last event performed by the user
13 console.log("hello from flask");
14 //sendJSON("{\"type\":\"empty\"}");
16 function update(id, msg) {
17 document.getElementById(id).innerHTML = msg;
20 function replayOfflineQueue() {
22 let queue = JSON.parse(localStorage.getItem("offlineQueue")) || [];
23 if (Array.isArray(queue)) {
24 queue.forEach(function (entry) {
25 updateRemote(entry.data, new Date(entry.time));
27 localStorage.removeItem("offlineQueue");
34 // Central function to update UI elements. To ensure that the UI is
35 // consistent, other code should only change state variables and then
36 // call this function. This function updates the UI to match the state.
40 let offline = updateRemote === undefined;
42 document.getElementById("local").style.display = !offline ? "none" : "block";
43 document.getElementById("remote").style.display = offline ? "none" : "block";
50 if (eventMsg !== undefined) {
51 update("eventMsg", eventMsg);
54 if (id_user !== undefined) {
55 document.getElementById("nextStep").innerHTML = "Now select a beverage on the coffee machineā¦";
56 } else if (flavorChosen !== undefined) {
57 document.getElementById("nextStep").innerHTML = "Enjoy your " + flavorChosen + "!";
60 if (timeToLogout !== undefined)
61 document.getElementById("logout_button").innerHTML = '<br>logout<br>(' + timeToLogout + ' s)';
64 console.log("updateUI error: ", err);
68 function hiddenUpdateRemote(json, time = new Date()) {
69 var msg = JSON.parse(json);
75 if (identifier_registration) {
76 ajax("POST", "user/identifier/add", JSON.stringify({ id: msg.uid }), "content");
78 addIdentifier_finish();
84 if (!identifier_registration) {
85 var flavor = getFlavor(msg.key);
87 addCoffee(flavor, time);
88 } else if (msg.key == "A") {
89 // When pressing 'Menu' key, logout to not count
90 // subsequent keys as coffee orders.
96 ajax(msg.method, msg.route, msg.data, msg.id);
103 function loadRemote(string) {
104 var xhr = new XMLHttpRequest();
105 xhr.onreadystatechange = function() {
106 if (this.readyState == 4) {
107 if (this.status == 200) {
108 update("remote", this.responseText);
109 updateRemote = hiddenUpdateRemote;
110 replayOfflineQueue();
112 clearTimeout(reloadTimer);
116 ajax("GET", "home", "", "content"); // Load home screen on first load or reload
118 // Cancel current timer for the case when loadRemote()
119 // was called multiple times (e.g. multiple ajax()
120 // calls failed simultaneously).
121 clearTimeout(reloadTimer);
122 reloadTimer = setTimeout(loadRemote, 1000);
126 xhr.open("GET", flask, true);
132 function ajax(method, route, data, id) {
133 var xhr = new XMLHttpRequest();
134 xhr.onreadystatechange = function() {
135 if (this.readyState == 4) {
136 if (this.status == 200) {
137 update(id, this.responseText);
140 updateRemote = undefined;
142 loadRemote(); // Try to contact the server periodically
145 var ajax_failure = JSON.stringify({
146 type: "ajax_failure",
152 let queue = JSON.parse(localStorage.getItem("offlineQueue")) || [];
153 queue.push({ time: Date.now(), data: ajax_failure });
155 localStorage.setItem("offlineQueue", JSON.stringify(queue));
164 xhr.open(method, flask + route, true);
165 xhr.withCredentials = true;
166 xhr.setRequestHeader("Content-type", "application/json");
167 if (method === "POST") {
176 ajax("POST", "login", id, "content");
178 countingTimeLogout(120);
183 ajax("GET", "logout", "", "content");
185 timeToLogout = undefined;
186 identifier_registration = false;
187 window.scrollTo(0, 0); // Scroll up
190 function countingTimeLogout(count_time)
192 clearTimeout(logoutTimer);
193 timeToLogout = count_time;
195 if (count_time == 0) {
198 logoutTimer = setTimeout(function() { countingTimeLogout(count_time - 1); }, 1000);
202 function renameUser() {
203 ajax("GET", "user/rename?name=" + document.getElementById("username").value, "", "content");
206 function getFlavor(letter) {
208 case "E": return "espresso";
209 case "C": return "cappuccino";
210 case "B": return "latte macchiato";
211 case "D": return "espresso lungo";
216 function addCoffee(flavor, time = new Date()) {
217 var data = JSON.stringify({
218 time: time.toISOString(),
222 ajax("POST", "coffee/add", data, "content");
223 flavorChosen = flavor;
225 countingTimeLogout(10); //mean 10 seconds
230 function addEvent(event_name, action_msg, time = new Date()) {
231 var data = JSON.stringify({
232 time: time.toISOString(),
233 event_name: event_name,
237 eventMsg = "You have " + action_msg + ". Thanks!"
238 ajax("POST", "event", data, "content");
239 window.scrollTo(0, 0); // Scroll up
244 function addIdentifier_start() {
245 identifier_registration = true;
246 document.getElementById("addIdentifier").disabled = true;
247 document.getElementById("labelIdentifier").style.visibility = "visible";
248 document.getElementById("abortIdentifier").disabled = false;
251 function addIdentifier_finish() {
252 identifier_registration = false;
253 document.getElementById("addIdentifier").disabled = false;
254 document.getElementById("labelIdentifier").style.visibility = "hidden";
255 document.getElementById("abortIdentifier").disabled = true;
258 function disableIdentifier(id) {
259 ajax("POST", "user/identifier/disable", JSON.stringify({ id: id }), "content");
262 function renameIdentifier(i) {
263 var data = JSON.stringify({
264 id: document.getElementById("identifier_" + i).innerText,
265 name: document.getElementById("identifier_name_" + i).value
268 ajax("POST", "user/identifier/rename", data, "content");
271 function sendLog(json) {
272 ajax("POST", "log", json, "log");
275 function tellCoffeebot(what)
277 ajax("POST", "tellCoffeebot", JSON.stringify({text: what}), "log");