diff --git a/src/injectscripts/all.js b/src/injectscripts/all.js index 245f2ec7..4ee3d583 100644 --- a/src/injectscripts/all.js +++ b/src/injectscripts/all.js @@ -133,6 +133,9 @@ whenWeAreReady(function () { Delete All Collections\ \
  • \ + User Guides\ +
  • \ +
  • \ About Lighthouse\
  • \ \ @@ -178,18 +181,6 @@ whenWeAreReady(function () { unitName + ' Today)\ \ - \ -
  • \ - Lighthouse Aided Dispatch (LAD!)\ -
  • \ -
  • \ - Register Tab For Remote Control\ -
  • \ \
  • \ @@ -207,7 +198,10 @@ whenWeAreReady(function () { Delete All Collections\
  • \
  • \ - About Lighthouse\ + User Guides\ +
  • \ +
  • \ + About Lighthouse\
  • \ \ \ diff --git a/src/pages/lib/shared_token_code.js b/src/pages/lib/shared_token_code.js index 420adaf9..edc1d33f 100644 --- a/src/pages/lib/shared_token_code.js +++ b/src/pages/lib/shared_token_code.js @@ -1,128 +1,89 @@ var $ = require('jquery'); var moment = require('moment'); -var periodicCheck = null +var periodicCheck = null; // wait for token to have loaded -export function fetchBeaconToken(apiHost, source, cb) { //when external vars have loaded - var waiting = setInterval(function () { //run every 1sec until we have loaded the page (dont hate me Sam) +export function fetchBeaconToken(apiHost, source, cb) { + const waiting = setInterval(function () { chrome.storage.local.get('beaconAPIToken-' + apiHost, function (data) { - var tokenJSON = JSON.parse(data['beaconAPIToken-' + apiHost]) - if (typeof tokenJSON.token !== "undefined" && typeof tokenJSON.expdate !== "undefined" && tokenJSON.token != '' && tokenJSON.expdate != '') { - var token = tokenJSON.token - var tokenexp = tokenJSON.expdate - clearInterval(waiting); //stop timer + const tokenJSON = JSON.parse(data['beaconAPIToken-' + apiHost]); + if (tokenJSON?.token && tokenJSON?.expdate) { + const { token, expdate: tokenexp } = tokenJSON; + clearInterval(waiting); // stop timer - if (periodicCheck == null) { - periodicCheck = setInterval(function () { - validateBeaconToken(apiHost, source) - }, 3e5); - } - - cb({ - token, - tokenexp - }); //call back + startTokenValidation(apiHost, source, cb); // Start periodic validation + cb({ token, tokenexp }); // callback with token } - }) + }); }, 200); } -// wait for token to have loaded -export function fetchBeaconTokenAndKeepReturningValidTokens(apiHost, source, cb) { //when external vars have loaded - var waiting = setInterval(function () { //run every 1sec until we have loaded the page (dont hate me Sam) +// wait for token to have loaded and keep returning valid tokens +export function fetchBeaconTokenAndKeepReturningValidTokens(apiHost, source, cb) { + const waiting = setInterval(function () { chrome.storage.local.get('beaconAPIToken-' + apiHost, function (data) { - var tokenJSON = JSON.parse(data['beaconAPIToken-' + apiHost]) - if (typeof tokenJSON.token !== "undefined" && typeof tokenJSON.expdate !== "undefined" && tokenJSON.token != '' && tokenJSON.expdate != '') { - var token = tokenJSON.token - var tokenexp = tokenJSON.expdate - clearInterval(waiting); //stop timer + const tokenJSON = JSON.parse(data['beaconAPIToken-' + apiHost]); + if (tokenJSON?.token && tokenJSON?.expdate) { + const { token, expdate: tokenexp } = tokenJSON; + clearInterval(waiting); // stop timer - if (periodicCheck == null) { - periodicCheck = setInterval(function () { - validateBeaconTokenKeepReturning(apiHost, source, cb) - }, 1 * 60 * 1000); // 1 minute - } - - cb({ - token, - tokenexp - }); //call back + startTokenValidation(apiHost, source, cb); // Start periodic validation + cb({ token, tokenexp }); // callback with token } - }) + }); }, 200); } -function validateBeaconTokenKeepReturning(apiHost, source, cb) { - fetchBeaconToken(apiHost, source, function ({ - token, - tokenexp - }) { - if (moment().isAfter(moment(tokenexp).subtract(5, "minutes"))) { - console.log("token expiry triggered. time to renew.") - $.ajax({ - type: 'GET', - url: source + "/Authorization/RefreshToken", - beforeSend: function (n) { - n.setRequestHeader("Authorization", "Bearer " + token) - }, - cache: false, - dataType: 'json', - complete: function (response, _textStatus) { - var token = response.responseJSON.access_token - var tokenexp = response.responseJSON.expires_at - chrome.storage.local.set({ - ['beaconAPIToken-' + apiHost]: JSON.stringify({ - token: token, - expdate: tokenexp - }) - }, function () { - console.log('local data set - beaconAPIToken') - cb({ - token, - tokenexp - }); //call back again - }) - console.log("successful token renew.") +// Start a single periodic token validation timer +function startTokenValidation(apiHost, source, cb) { + if (periodicCheck != null) return; // Avoid multiple timers + + periodicCheck = setInterval(function () { + chrome.storage.local.get('beaconAPIToken-' + apiHost, function (data) { + const tokenJSON = JSON.parse(data['beaconAPIToken-' + apiHost]); + if (tokenJSON?.token && tokenJSON?.expdate) { + const { token, expdate: tokenexp } = tokenJSON; + + if (moment().isAfter(moment(tokenexp).subtract(5, "minutes"))) { + renewToken(apiHost, source, token, cb); + } else { + console.log('API token still valid'); } - }) - } else { - console.log('api token still valid') - } - }) + } + }); + }, 1 * 60 * 1000); // Check every 1 minute } - -export function validateBeaconToken(apiHost, source) { - fetchBeaconToken(apiHost, source, function ({ - token, - tokenexp - }) { - if (moment().isAfter(moment(tokenexp).subtract(5, "minutes"))) { - console.log("token expiry triggered. time to renew.") - $.ajax({ - type: 'GET', - url: source + "/Authorization/RefreshToken", - beforeSend: function (n) { - n.setRequestHeader("Authorization", "Bearer " + token) - }, - cache: false, - dataType: 'json', - complete: function (response, _textStatus) { - var token = response.responseJSON.access_token - var tokenexp = response.responseJSON.expires_at - chrome.storage.local.set({ - ['beaconAPIToken-' + apiHost]: JSON.stringify({ - token: token, - expdate: tokenexp - }) - }, function () { - console.log('local data set - beaconAPIToken') +// Renew the token +function renewToken(apiHost, source, token, cb) { + console.log("Token expiry triggered. Attempting to renew."); + $.ajax({ + type: 'GET', + url: source + "/Authorization/RefreshToken", + beforeSend: function (n) { + n.setRequestHeader("Authorization", "Bearer " + token); + }, + cache: false, + dataType: 'json', + complete: function (response, _textStatus) { + if (response.status === 200 && response.responseJSON) { + const newToken = response.responseJSON.access_token; + const newTokenExp = response.responseJSON.expires_at; + chrome.storage.local.set({ + ['beaconAPIToken-' + apiHost]: JSON.stringify({ + token: newToken, + expdate: newTokenExp }) - console.log("successful token renew.") - } - }) - } else { - console.log('api token still valid') + }, function () { + console.log('Local data set - beaconAPIToken'); + cb({ token: newToken, tokenexp: newTokenExp }); // callback with new token + }); + console.log("Successful token renewal."); + } else { + console.error("Token renewal failed. Stopping further attempts."); + clearInterval(periodicCheck); // Stop further attempts + periodicCheck = null; + } } - }) + }); } diff --git a/src/pages/tasking/components/asset_popup.js b/src/pages/tasking/components/asset_popup.js index c8746abc..698a7bcf 100644 --- a/src/pages/tasking/components/asset_popup.js +++ b/src/pages/tasking/components/asset_popup.js @@ -99,17 +99,17 @@ export function buildAssetPopupKO() {
    - -
    -
    +
    `; diff --git a/src/pages/tasking/components/job_popup.js b/src/pages/tasking/components/job_popup.js index 8d3f257e..716a2833 100644 --- a/src/pages/tasking/components/job_popup.js +++ b/src/pages/tasking/components/job_popup.js @@ -139,7 +139,12 @@ export function buildJobPopupKO() { +
  • + +
  • +
  • + @@ -559,7 +567,8 @@ -
    +
    - @@ -1397,7 +1406,8 @@
    @@ -1498,7 +1508,8 @@ -
    +
    -
    @@ -1561,10 +1571,10 @@ - - - - + + + + @@ -2322,13 +2332,13 @@

    - +

    @@ -2339,16 +2349,16 @@

    - Pinned teams:  •  - Pinned incidents:
    @@ -2357,7 +2367,7 @@

    -
    Pinned Teams
    +
    Starred Teams
    @@ -2376,7 +2386,7 @@

    -
    Pinned Incidents
    +
    Starred Incidents
    @@ -2438,7 +2448,7 @@

    + css: { 'expanded-input': config.loadExpanded }">

    + + + diff --git a/styles/pages/tasking.css b/styles/pages/tasking.css index 549ccb9a..36509473 100644 --- a/styles/pages/tasking.css +++ b/styles/pages/tasking.css @@ -257,6 +257,7 @@ td.chev[draggable='true'] * { .sidebar { width: var(--sidebar-w, 420px); + min-width: 1010px; display: flex; flex-direction: column; } @@ -478,6 +479,14 @@ table thead th.sortable .th-label { white-space: nowrap; } +table thead th.not-sortable { + min-width: 0; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; +} + + table thead th.sortable .sort-icon { flex: 0 0 auto; /* never wrap/shrink */ } @@ -1405,13 +1414,13 @@ tr.job:hover { --job-cols: 30px /* chev */ 20px /* pin */ - 0.28fr /* Id */ + 0.38fr /* Id */ 0.5fr /* Received */ 0.3fr /* HQ */ 0.3fr /* Type */ 1.5fr /* Situation */ 0.5fr /* Status */ - 1.0fr; /* Address */ + 0.9fr; /* Address */ } /* body */ @@ -2163,4 +2172,6 @@ input[type="search"]::-ms-clear { .map-popups-hidden .leaflet-popup-pane, .map-popups-hidden .leaflet-tooltip-pane { display: none !important; -} \ No newline at end of file +} + +.fa-center { line-height: inherit!important; vertical-align: middle; }