Skip to content

Commit

Permalink
Add Button for overall turn off #100
Browse files Browse the repository at this point in the history
At the lite dashboard
  • Loading branch information
haimkastner committed Jan 21, 2020
1 parent 3285003 commit 5c93b7a
Show file tree
Hide file tree
Showing 3 changed files with 163 additions and 47 deletions.
33 changes: 33 additions & 0 deletions frontend/src/light-app/index.css
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,39 @@ body {
text-align: center;
}

.hide {
display: none;
}

.power-off-container {
position: absolute;
margin: 0;
padding: 0;
}

#power-on {
cursor: pointer;
fill: #6dbdb9;
color: #6dbdb9;
}

.power-on-text {
font-size: xx-small;
text-align: center;
margin: 0;
padding: 0;
}

#power-off {
fill: #737471;
color: #737471;
}

#power-sync {
fill: #737471;
color: #737471;
}

.dashboard-link {
color: rgb(155, 155, 232);
font-family: helvetica;
Expand Down
29 changes: 28 additions & 1 deletion frontend/src/light-app/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,35 @@
</head>

<body>
<div class="power-off-container">
<div id="power-on" onclick="powerAllOff()">
<p class="power-on-text power-on-item">Turn Off All</p>
<svg class="power-on-item" xmlns="http://www.w3.org/2000/svg" width="50" height="50" viewBox="0 0 24 24">
<path fill="none" d="M0 0h24v24H0z" />
<path
d="M13 3h-2v10h2V3zm4.83 2.17l-1.42 1.42C17.99 7.86 19 9.81 19 12c0 3.87-3.13 7-7 7s-7-3.13-7-7c0-2.19 1.01-4.14 2.58-5.42L6.17 5.17C4.23 6.82 3 9.26 3 12c0 4.97 4.03 9 9 9s9-4.03 9-9c0-2.74-1.23-5.18-3.17-6.83z" />
</svg>
</div>
<div id="power-off" class="hide">
<div style="margin-top: 13px;"></div>
<svg xmlns="http://www.w3.org/2000/svg" width="50" height="50" viewBox="0 0 24 24">
<path fill="none" d="M0 0h24v24H0z" />
<path
d="M13 3h-2v10h2V3zm4.83 2.17l-1.42 1.42C17.99 7.86 19 9.81 19 12c0 3.87-3.13 7-7 7s-7-3.13-7-7c0-2.19 1.01-4.14 2.58-5.42L6.17 5.17C4.23 6.82 3 9.26 3 12c0 4.97 4.03 9 9 9s9-4.03 9-9c0-2.74-1.23-5.18-3.17-6.83z" />
</svg>
</div>
<div id="power-sync" class="hide">
<div style="margin-top: 13px;"></div>
<svg xmlns="http://www.w3.org/2000/svg" width="50" height="50" viewBox="0 0 24 24">
<path d="M0 0h24v24H0z" fill="none" />
<path
d="M6 10c-1.1 0-2 .9-2 2s.9 2 2 2 2-.9 2-2-.9-2-2-2zm12 0c-1.1 0-2 .9-2 2s.9 2 2 2 2-.9 2-2-.9-2-2-2zm-6 0c-1.1 0-2 .9-2 2s.9 2 2 2 2-.9 2-2-.9-2-2-2z" />
</svg>
</div>
</div>

<div>
<a class="dashboard-link" target="_blank" href="/">Click here to move to the full dashboard version</a>
<a class="dashboard-link" target="_blank" href="/">Full dashboard</a>
</div>
<div id="welcome-message">
<h1 style="text-align:center;">Welcome To Casanet Lite Dashboard</h1>
Expand Down
148 changes: 102 additions & 46 deletions frontend/src/light-app/index.js
Original file line number Diff line number Diff line change
@@ -1,16 +1,19 @@
/** Get the environments */
let environments = {
API_URL: "http://127.0.0.1:3000/API",
DASHBOARD_DOMAIN: ""
API_URL: 'http://127.0.0.1:3000/API',
DASHBOARD_DOMAIN: '',
};

/** Flag to know if the 'power off' syncing */
let isSync = false;

let domainAlert = () => {
if (document.baseURI.includes(environments.DASHBOARD_DOMAIN)) {
return;
}

const result = confirm(
`The address of the service has changed and you will soon get off the air, please move to our new address!\n\n${environments.DASHBOARD_DOMAIN}\n\nPress 'OK' to move the new home`
`The address of the service has changed and you will soon get off the air, please move to our new address!\n\n${environments.DASHBOARD_DOMAIN}\n\nPress 'OK' to move the new home`,
);
if (!result) {
return;
Expand All @@ -28,13 +31,13 @@ let fetchEnvironments = () => {
}

if (xmlhttp.status === 401 || xmlhttp.status === 403) {
alert("GET ENVIRONMENTS FAIL");
alert('GET ENVIRONMENTS FAIL');
return;
}

getMinionsFail(xmlhttp.responseText);
};
xmlhttp.open("GET", "/light-app/environments.json", false);
xmlhttp.open('GET', '/light-app/environments.json', false);
xmlhttp.send();
};

Expand All @@ -45,40 +48,43 @@ fetchEnvironments();
* Redirect to auth page.
*/
let accessFail = () => {
alert("ACCESS FORBIDDEN, redirecting to auth page...");
window.location.href = "/#/login";
alert('ACCESS FORBIDDEN, redirecting to auth page...');
window.location.href = '/#/login';
};

let getMinionsFail = msg => {
if (confirm(`GET MINIONS FAIL: \n${msg},\n\n\nPress "OK" to retry`)) {
patchMinions();
petchMinions();
}
};

/**
* Generate HTML button for given minion
* @param {*} minion A minion
* @returns A DOM button object for the given minion
* @returns A DOM button object for the given minion
*/
let generateMinionButton = minion => {
/** Create button element */
const minionButton = document.createElement("a");
const minionButton = document.createElement('a');

/** Insert name */
minionButton.innerText = minion.name;

try {
/** Set correct class for current status */
minionButton.className = `button button--ghost button--ghost--${
minion.minionStatus[minion.minionType].status
}`;
minionButton.className = `button button--ghost button--ghost--${minion.minionStatus[minion.minionType].status}`;

if (!isSync && minion.minionStatus[minion.minionType].status === 'on') {
// In case the minion status are 'on' allow 'power-all-off' button
setViewPowerOn();
}

if (!minion.isProperlyCommunicated) {
minionButton.className = `button button--ghost button--ghost--err`;
}
} catch (error) {
minion.minionStatus[minion.minionType] = {
status: "off"
status: 'off',
};
minionButton.className = `button button--ghost button--ghost--err`;
}
Expand All @@ -104,28 +110,34 @@ let generateMinions = minions => {
});

const rooms = minions.reduce((rooms, minion) => {
minion.room = minion.room ? minion.room : "";
minion.room = minion.room ? minion.room : '';
rooms[minion.room] = rooms[minion.room] ? rooms[minion.room] : [];
rooms[minion.room].push(minion);
return rooms;
}, {});

/** Get the list holder element */
const welcomeElement = document.getElementById("welcome-message");
welcomeElement.innerHTML = "";
const welcomeElement = document.getElementById('welcome-message');
welcomeElement.innerHTML = '';

/** Get the list holder element */
const listElement = document.getElementById("minions-container");
const listElement = document.getElementById('minions-container');

/** Set list empty */
listElement.innerHTML = "";
listElement.innerHTML = '';

if (!isSync) {
// If the power off not currently sync, set power off,
// and in case any of the minion status are 'on' then call to 'setViewPowerOn()'
setViewPowerOff();
}

for (const [roomName, roomMinions] of Object.entries(rooms)) {
const roomDiv = document.createElement("div");
roomDiv.className = "room";
const roomDiv = document.createElement('div');
roomDiv.className = 'room';

const roomTitle = document.createElement("h3");
roomTitle.className = "room-name";
const roomTitle = document.createElement('h3');
roomTitle.className = 'room-name';
roomTitle.innerText = roomName;

roomDiv.appendChild(roomTitle);
Expand All @@ -140,7 +152,7 @@ let generateMinions = minions => {
};

/** Get minions from server */
let patchMinions = () => {
let petchMinions = () => {
// compatible with IE7+, Firefox, Chrome, Opera, Safari
const xmlhttp = new XMLHttpRequest();
xmlhttp.withCredentials = true;
Expand All @@ -157,21 +169,21 @@ let patchMinions = () => {

getMinionsFail(xmlhttp.responseText);
};
xmlhttp.open("GET", `${environments.API_URL}/minions`, true);
xmlhttp.open('GET', `${environments.API_URL}/minions`, true);
xmlhttp.send();
};

/** Toggle minion status on click */
let buttonClicked = (element, minion) => {
if (minion.sync) {
if (minion.sync || isSync) {
return;
}

minion.sync = true;
element.className = element.className + " button--slicein--sync";
element.className = element.className + ' button--slicein--sync';

const setStatus = JSON.parse(JSON.stringify(minion.minionStatus));
setStatus[minion.minionType].status =
setStatus[minion.minionType].status === "on" ? "off" : "on";
setStatus[minion.minionType].status = setStatus[minion.minionType].status === 'on' ? 'off' : 'on';

// compatible with IE7+, Firefox, Chrome, Opera, Safari
const xmlhttp = new XMLHttpRequest();
Expand All @@ -183,51 +195,95 @@ let buttonClicked = (element, minion) => {
}

if (xmlhttp.status === 204) {
patchMinions();
petchMinions();
return;
}

element.className = `button button--ghost button--ghost--${
minion.minionStatus[minion.minionType].status
}`;
element.className = `button button--ghost button--ghost--${minion.minionStatus[minion.minionType].status}`;

if (xmlhttp.status === 401 || xmlhttp.status === 403) {
accessFail();
}
};

xmlhttp.open(
"PUT",
`${environments.API_URL}/minions/${minion.minionId}`,
true
);
xmlhttp.setRequestHeader("Content-type", "application/json; charset=utf-8");
xmlhttp.open('PUT', `${environments.API_URL}/minions/${minion.minionId}`, true);
xmlhttp.setRequestHeader('Content-type', 'application/json; charset=utf-8');
xmlhttp.send(JSON.stringify(setStatus));
};

let setViewPowerOn = () => {
const powerOnContainer = document.getElementById('power-on');
const powerOffContainer = document.getElementById('power-off');
const powerSyncContainer = document.getElementById('power-sync');

powerOnContainer.className = '';
powerOffContainer.className = 'hide';
powerSyncContainer.className = 'hide';
};

let setViewPowerOff = () => {
const powerOnContainer = document.getElementById('power-on');
const powerOffContainer = document.getElementById('power-off');
const powerSyncContainer = document.getElementById('power-sync');

powerOnContainer.className = 'hide';
powerOffContainer.className = '';
powerSyncContainer.className = 'hide';
};

let setViewPowerSync = () => {
const powerOnContainer = document.getElementById('power-on');
const powerOffContainer = document.getElementById('power-off');
const powerSyncContainer = document.getElementById('power-sync');

powerOnContainer.className = 'hide';
powerOffContainer.className = 'hide';
powerSyncContainer.className = '';
};

let powerAllOff = () => {
isSync = true;

// Mark view as sync
setViewPowerSync();

const xmlhttp = new XMLHttpRequest();
xmlhttp.onload = () => {
if (xmlhttp.readyState === 4 && xmlhttp.status == 204) {
isSync = false;
petchMinions();
return;
}

alert('POWER OFF FAIL');
};
xmlhttp.open('PUT', `${environments.API_URL}/minions/power-off`, true);
xmlhttp.send();
};

/** On start. get and generate minions */
patchMinions();
petchMinions();

/** SSE */
var evtSource = new EventSource(`${environments.API_URL}/feed/minions`, {
withCredentials: true
withCredentials: true,
});

evtSource.onmessage = e => {
if (e.data === '"init"') {
return;
}
patchMinions();
petchMinions();
};

/** PWA */
if (localStorage.getItem("use-sw") === "true" && "serviceWorker" in navigator) {
if (localStorage.getItem('use-sw') === 'true' && 'serviceWorker' in navigator) {
navigator.serviceWorker
.register("/light-app/service-worker.js")
.register('/light-app/service-worker.js')
.then(function(registration) {
console.log("Registration successful, scope is:", registration.scope);
console.log('Registration successful, scope is:', registration.scope);
})
.catch(function(error) {
console.warn("Service worker registration failed, error:", error);
console.warn('Service worker registration failed, error:', error);
});
}

0 comments on commit 5c93b7a

Please sign in to comment.