diff --git a/cypress/integration/layout.spec.js b/cypress/integration/layout.spec.js --- a/cypress/integration/layout.spec.js +++ b/cypress/integration/layout.spec.js @@ -1,11 +1,12 @@ /** - * Copyright (C) 2019 The Software Heritage developers + * Copyright (C) 2019-2020 The Software Heritage developers * See the AUTHORS file at the top-level directory of this distribution * License: GNU Affero General Public License version 3, or any later version * See top-level LICENSE file for more information */ const url = '/browse/help/'; +const statusUrl = 'https://status.softwareheritage.org'; describe('Test top-bar', function() { beforeEach(function() { @@ -103,6 +104,88 @@ .should('have.class', 'container') .should('not.have.class', 'container-fluid'); }); + + function genStatusResponse(status, statusCode) { + return { + 'result': { + 'status': [ + { + 'id': '5f7c4c567f50b304c1e7bd5f', + 'name': 'Save Code Now', + 'updated': '2020-11-30T13:51:21.151Z', + 'status': 'Operational', + 'status_code': 100 + }, + { + 'id': '5f7c4c6f8338bc04b7f476fe', + 'name': 'Source Code Crawlers', + 'updated': '2020-11-30T13:51:21.151Z', + 'status': status, + 'status_code': statusCode + } + ] + } + }; + } + + it('should display swh status widget when data are available', function() { + const statusTestData = [ + { + status: 'Operational', + statusCode: 100, + color: 'green' + }, + { + status: 'Scheduled Maintenance', + statusCode: 200, + color: 'blue' + }, + { + status: 'Degraded Performance', + statusCode: 300, + color: 'yellow' + }, + { + status: 'Partial Service Disruption', + statusCode: 400, + color: 'yellow' + }, + { + status: 'Service Disruption', + statusCode: 500, + color: 'red' + }, + { + status: 'Security Event', + statusCode: 600, + color: 'red' + } + ]; + + for (let std of statusTestData) { + cy.server(); + cy.route({ + url: `${statusUrl}/**`, + response: genStatusResponse(std.status, std.statusCode) + }).as('getSwhStatusData'); + cy.visit(url); + cy.wait('@getSwhStatusData'); + cy.get('.swh-current-status-indicator').should('have.class', std.color); + cy.get('#swh-current-status-description').should('have.text', std.status); + } + }); + + it('should not display swh status widget when data are not available', function() { + cy.server(); + cy.route({ + url: `${statusUrl}/**`, + response: {} + }).as('getSwhStatusData'); + cy.visit(url); + cy.wait('@getSwhStatusData'); + cy.get('.swh-current-status').should('not.be.visible'); + }); + }); describe('Test navbar', function() { diff --git a/swh/web/assets/src/bundles/webapp/index.js b/swh/web/assets/src/bundles/webapp/index.js --- a/swh/web/assets/src/bundles/webapp/index.js +++ b/swh/web/assets/src/bundles/webapp/index.js @@ -24,3 +24,4 @@ export * from './badges'; export * from './sentry'; export * from './math-typesetting'; +export * from './status-widget'; diff --git a/swh/web/assets/src/bundles/webapp/status-widget.css b/swh/web/assets/src/bundles/webapp/status-widget.css new file mode 100644 --- /dev/null +++ b/swh/web/assets/src/bundles/webapp/status-widget.css @@ -0,0 +1,38 @@ +/** + * Copyright (C) 2020 The Software Heritage developers + * See the AUTHORS file at the top-level directory of this distribution + * License: GNU Affero General Public License version 3, or any later version + * See top-level LICENSE file for more information + */ + +.swh-current-status-indicator { + width: 12px; + height: 12px; + margin: 0 0 0 5px; + display: inline-block; + border-radius: 6px; +} + +.swh-current-status-indicator.small { + width: 8px; + height: 8px; + margin: 0 0 0 5px; + display: inline-block; + border-radius: 4px; +} + +.swh-current-status-indicator.green { + background: #27ae60; +} + +.swh-current-status-indicator.yellow { + background: #ffa837; +} + +.swh-current-status-indicator.red { + background: #c44031; +} + +.swh-current-status-indicator.blue { + background: #00aaf0; +} diff --git a/swh/web/assets/src/bundles/webapp/status-widget.js b/swh/web/assets/src/bundles/webapp/status-widget.js new file mode 100644 --- /dev/null +++ b/swh/web/assets/src/bundles/webapp/status-widget.js @@ -0,0 +1,50 @@ +/** + * Copyright (C) 2020 The Software Heritage developers + * See the AUTHORS file at the top-level directory of this distribution + * License: GNU Affero General Public License version 3, or any later version + * See top-level LICENSE file for more information + */ + +import './status-widget.css'; + +const statusCodeColor = { + '100': 'green', // Operational + '200': 'blue', // Scheduled Maintenance + '300': 'yellow', // Degraded Performance + '400': 'yellow', // Partial Service Disruption + '500': 'red', // Service Disruption + '600': 'red' // Security Event +}; + +export function initStatusWidget(statusDataURL) { + $('.swh-current-status-indicator').ready(() => { + let maxStatusCode = ''; + let maxStatusDescription = ''; + let sc = ''; + let sd = ''; + fetch(statusDataURL) + .then(resp => resp.json()) + .then(data => { + for (let s of data.result.status) { + sc = s.status_code; + sd = s.status; + if (maxStatusCode < sc) { + maxStatusCode = sc; + maxStatusDescription = sd; + } + } + if (maxStatusCode === '') { + $('.swh-current-status').remove(); + return; + } + $('.swh-current-status-indicator').removeClass('green'); + $('.swh-current-status-indicator').addClass(statusCodeColor[maxStatusCode]); + $('#swh-current-status-description').text(maxStatusDescription); + }) + .catch(e => { + console.log(e); + $('.swh-current-status').remove(); + }); + + }); +} diff --git a/swh/web/common/utils.py b/swh/web/common/utils.py --- a/swh/web/common/utils.py +++ b/swh/web/common/utils.py @@ -265,6 +265,7 @@ "keycloak": config["keycloak"], "site_base_url": request.build_absolute_uri("/"), "DJANGO_SETTINGS_MODULE": os.environ["DJANGO_SETTINGS_MODULE"], + "status": config["status"], } diff --git a/swh/web/config.py b/swh/web/config.py --- a/swh/web/config.py +++ b/swh/web/config.py @@ -96,6 +96,13 @@ "dict", {"server_url": "http://graph.internal.softwareheritage.org:5009/graph/"}, ), + "status": ( + "dict", + { + "server_url": "https://status.softwareheritage.org/", + "json_path": "1.0/status/578e5eddcdc0cc7951000520", + }, + ), } swhweb_config = {} # type: Dict[str, Any] diff --git a/swh/web/templates/layout.html b/swh/web/templates/layout.html --- a/swh/web/templates/layout.html +++ b/swh/web/templates/layout.html @@ -108,6 +108,11 @@ Donate
  • + + Operational + + {% url 'logout' as logout_url %} {% if user.is_authenticated %} Logged in as @@ -252,6 +257,9 @@