Skip to content

Commit

Permalink
Merge pull request #348 from JustinMacaulay/feature/outage-banner
Browse files Browse the repository at this point in the history
VS-6971 Outage Banner
  • Loading branch information
sam-warren authored Nov 14, 2024
2 parents 49053d0 + 68d3b02 commit 027c220
Show file tree
Hide file tree
Showing 8 changed files with 169 additions and 2 deletions.
15 changes: 15 additions & 0 deletions vsd-app/ClientApp/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions vsd-app/ClientApp/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@
"jasmine-reporters": "^2.4.0",
"jasmine2-protractor-utils": "^1.3.0",
"moment": "^2.22.2",
"moment-timezone": "^0.5.46",
"mygovbc-bootstrap-theme": "^0.4.1",
"ng-busy": "^7.0.0",
"ngx-bootstrap": "^3.0.0",
Expand Down
10 changes: 9 additions & 1 deletion vsd-app/ClientApp/src/app/app.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,14 @@
<div>
<main class="app-content">
<div class="app-main">
<div
*ngIf="!error && isOutage()"
class="text-center warning"
>
<h1 class="warning">Site Outage</h1>
<h2 class="warning"><b>{{ configuration.outageMessage }}</b>></h2>
<h2 class="warning"><b>{{ generateOutageDateMessage() }}</b>></h2>
</div>
<breadcrumb></breadcrumb>
<router-outlet></router-outlet>
</div>
Expand Down Expand Up @@ -54,4 +62,4 @@
</div>
</nav>
</footer>
</div>
</div>
4 changes: 4 additions & 0 deletions vsd-app/ClientApp/src/app/app.component.scss
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,10 @@ header {
border-bottom: 4px solid #fcba19;
}

.warning{
color: red !important;
}

.title {
font-weight: Semi-bold;
font-size: 30px;
Expand Down
34 changes: 33 additions & 1 deletion vsd-app/ClientApp/src/app/app.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ import { isDevMode } from '@angular/core';
import 'rxjs/add/operator/filter';
import { HeaderTitleService } from './services/titile.service';
import { LookupService } from './services/lookup.service';
import { ConfigService } from "./services/config.service";
import { Configuration } from "./interfaces/configuration.interface";
import * as moment from 'moment-timezone';

@Component({
selector: 'app-root',
Expand All @@ -13,14 +16,17 @@ import { LookupService } from './services/lookup.service';
export class AppComponent implements OnInit {
title = '';
previousUrl: string;
configuration: Configuration;
error = false;
public isNewUser: boolean;
public isDevMode: boolean;

constructor(
private renderer: Renderer2,
private router: Router,
private headerTitleService: HeaderTitleService,
private lookupService: LookupService
private lookupService: LookupService,
private configService: ConfigService,
) {
this.isDevMode = isDevMode();
this.router.events.subscribe((event) => {
Expand Down Expand Up @@ -50,6 +56,32 @@ export class AppComponent implements OnInit {
this.lookupService.cvapCounsellingEmail = res.cvapCounsellingEmail;
}
});

this.configService.load()
.then((configuration) => {
console.log("Fetched Configuration:", configuration);
this.configuration = configuration;
})
.catch((error) => {
console.error("Failed to fetch configuration:", error);
this.error = error;
});
}

isOutage() {
if (!this.configuration || !this.configuration.outageEndDate || !this.configuration.outageStartDate || !this.configuration.outageMessage) {
return false;
}
const currentDate = moment().tz("America/Vancouver");
const outageStartDate = moment(this.configuration.outageStartDate).tz("America/Vancouver");
const outageEndDate = moment(this.configuration.outageEndDate).tz("America/Vancouver");
return currentDate.isBetween(outageStartDate, outageEndDate, null, '[]');
}

generateOutageDateMessage(): string {
const startDate = moment(this.configuration.outageStartDate).tz("America/Vancouver").format("MMMM Do YYYY, h:mm a");
const endDate = moment(this.configuration.outageEndDate).tz("America/Vancouver").format("MMMM Do YYYY, h:mm a");
return "The system will be down for maintenance from " + startDate + " to " + endDate;
}

isIE10orLower() {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
export interface Configuration {
outageStartDate?: string;
outageEndDate?: string;
outageMessage?: string;
}
45 changes: 45 additions & 0 deletions vsd-app/ClientApp/src/app/services/config.service.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
import { Injectable } from '@angular/core';
import { HttpClient, HttpHeaders } from '@angular/common/http';
import { Observable, throwError } from 'rxjs';
import { catchError } from 'rxjs/operators';
import { Configuration } from '../interfaces/configuration.interface';
import {environment} from "../../environments/environment";

@Injectable({
providedIn: 'root'
})
export class ConfigService{
headers: HttpHeaders = new HttpHeaders({
'Content-Type': 'application/json'
});
baseUrl = environment.apiRootUrl;
apiPath = this.baseUrl.concat('api/Configuration');

constructor(
private http: HttpClient,
) { }

public async load(): Promise<Configuration> {
try {
return await
this.http.get<Configuration>(this.apiPath, { headers: this.headers })
.pipe(catchError(this.handleError)).toPromise();
} catch (error) {
this.handleError(error);
throw error;
}
}

protected handleError(err): Observable<never> {
let errorMessage = '';
if (err.error instanceof ErrorEvent) {
// A client-side or network error occurred. Handle it accordingly.
errorMessage = err.error.message;
} else {
// The backend returned an unsuccessful response code.
// The response body may contain clues as to what went wrong,
errorMessage = `Backend returned code ${err.status}, body was: ${err.message}`;
}
return throwError(errorMessage);
}
}
57 changes: 57 additions & 0 deletions vsd-app/Controllers/ConfigurationController.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
using System;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Logging;
using Microsoft.AspNetCore.Authorization;

namespace Gov.Cscp.VictimServices.Public.Controllers
{
[Route("api/[controller]")]
[ApiController]
public class ConfigurationController : ControllerBase
{
private readonly ILogger<ConfigurationController> logger;
private readonly IConfiguration configuration;

public ConfigurationController(ILogger<ConfigurationController> logger, IConfiguration configuration)
{
this.logger = logger;
this.configuration = configuration;
}

[AllowAnonymous]
[HttpGet]
public IActionResult GetConfiguration()
{
try
{
var config = new Configuration
{
OutageMessage = configuration.GetValue<string>("CONFIGURATION_OUTAGEINFORMATION_MESSAGE"),
OutageStartDate = configuration.GetValue<string>("CONFIGURATION_OUTAGEINFORMATION_STARTDATE"),
OutageEndDate = configuration.GetValue<string>("CONFIGURATION_OUTAGEINFORMATION_ENDDATE")
};

if (string.IsNullOrEmpty(config.OutageMessage) || string.IsNullOrEmpty(config.OutageStartDate) || string.IsNullOrEmpty(config.OutageEndDate))
{
return Ok();
};

return Ok(config);
}
catch (Exception ex)
{
logger.LogError(ex, "Failed to retrieve configuration information.");
return StatusCode(StatusCodes.Status500InternalServerError);
}
}
}
}

public class Configuration
{
public string OutageMessage { get; set; }
public string OutageStartDate { get; set; }
public string OutageEndDate { get; set; }
};

0 comments on commit 027c220

Please sign in to comment.