Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
69 changes: 69 additions & 0 deletions src/main/controllers/style-guide/CrownFirmPddaListController.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
import { PipRequest } from '../../models/request/PipRequest';
import { Response } from 'express';
import { formatMetaDataListType, isUnexpectedListType, isValidList, isValidListType } from '../../helpers/listHelper';
import { HttpStatusCode } from 'axios';
import { cloneDeep } from 'lodash';
import { ListParseHelperService } from '../../service/ListParseHelperService';
import { LocationService } from '../../service/LocationService';
import { PublicationService } from '../../service/PublicationService';
import { formatDate } from '../../helpers/dateTimeHelper';
import { CrownFirmPddaListService } from '../../service/listManipulation/CrownFirmPddaListService';

const publicationService = new PublicationService();
const locationService = new LocationService();
const helperService = new ListParseHelperService();
const crownFirmPddaListService = new CrownFirmPddaListService();

const listType = 'crown-firm-pdda-list';

export default class CrownFirmPddaListController {
public async get(req: PipRequest, res: Response): Promise<void> {
const artefactId = req.query.artefactId as string;
const payload = await publicationService.getIndividualPublicationJson(artefactId, req.user?.['userId']);
const metadata = await publicationService.getIndividualPublicationMetadata(artefactId, req.user?.['userId']);
const metadataListType = formatMetaDataListType(metadata);

if (isValidList(payload, metadata) && isValidListType(metadataListType, listType)) {
const listData = crownFirmPddaListService.processPayload(payload as JSON, req.lng);
const returnedLocation = await locationService.getLocationById(metadata['locationId']);
const locationName = locationService.findCourtName(returnedLocation, req.lng, listType);

const firmListData = payload['FirmList'];
const listHeader = firmListData.ListHeader;
const publishedDate = helperService.publicationDateInUkTime(listHeader.PublishedTime, req.lng);
const publishedTime = helperService.publicationTimeInUkTime(listHeader.PublishedTime);
const startDate = formatDate(
crownFirmPddaListService.toIsoDate(listHeader.StartDate),
'dd MMMM yyyy',
req.lng
);
const endDate = listHeader.EndDate
? formatDate(crownFirmPddaListService.toIsoDate(listHeader.EndDate), 'dd MMMM yyyy', req.lng)
: '';
const version = listHeader.Version;
const venueAddress = crownFirmPddaListService.formatAddress(firmListData.CrownCourt.CourtHouseAddress);

res.render(`style-guide/${listType}`, {
...cloneDeep(req.i18n.getDataByLanguage(req.lng)[listType]),
...cloneDeep(req.i18n.getDataByLanguage(req.lng)['list-template']),
listData: listData,
locationName: locationName,
provenance: metadata.provenance,
publishedDate,
publishedTime,
startDate,
endDate,
version,
venueAddress,
});
} else if (
payload === HttpStatusCode.NotFound ||
metadata === HttpStatusCode.NotFound ||
isUnexpectedListType(metadataListType, listType)
) {
res.render('list-not-found', req.i18n.getDataByLanguage(req.lng)['list-not-found']);
} else {
res.render('error', req.i18n.getDataByLanguage(req.lng).error);
}
}
}
16 changes: 12 additions & 4 deletions src/main/resources/listLookup.json
Original file line number Diff line number Diff line change
Expand Up @@ -673,7 +673,7 @@
"shortenedFriendlyName": "London Circuit Commercial Court (KB) Daily Cause List",
"url": "london-circuit-commercial-court-kb-daily-cause-list",
"jurisdictionTypes": ["High Court"],
"restrictedProvenances": [],
"restrictedProvenances": [],
"defaultSensitivity": "",
"isNonStrategic": true
},
Expand Down Expand Up @@ -822,9 +822,7 @@
"welshFriendlyName": "Rhestr Achosion Dyddiol y Llys Apêl (Adran Sifil)",
"shortenedFriendlyName": "Court of Appeal (Civil Division) Daily Cause List",
"url": "court-of-appeal-civil-daily-cause-list",
"jurisdictionTypes": [
"Court of Appeal (Civil Division)"
],
"jurisdictionTypes": ["Court of Appeal (Civil Division)"],
"restrictedProvenances": [],
"defaultSensitivity": "",
"isNonStrategic": true
Expand Down Expand Up @@ -929,5 +927,15 @@
"restrictedProvenances": [],
"defaultSensitivity": "CLASSIFIED",
"isNonStrategic": false
},
"CROWN_FIRM_PDDA_LIST": {
"friendlyName": "Crown Firm PDDA List",
"welshFriendlyName": "Rhestr PDDA Cwmni Llys y Goron",
"shortenedFriendlyName": "Crown Firm PDDA List",
"url": "crown-firm-pdda-list",
"jurisdictionTypes": ["Crown Court"],
"restrictedProvenances": [],
"defaultSensitivity": "CLASSIFIED",
"isNonStrategic": false
}
}
28 changes: 28 additions & 0 deletions src/main/resources/locales/cy/crown-firm-pdda-list.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
{
"title": "Rhestr Cwmni Llys y Goron",
"heading": "Rhestr Cwmni Llys y Goron ar gyfer",
"listDate": "Rhestr ar gyfer",
"to": "i",
"listUpdated": "Diweddarwyd diwethaf",
"at": "am",
"versionText": "Fersiwn",
"restrictionInformationHeading": "Cyfyngiadau ar gyhoeddi neu ysgrifennu am yr achosion hyn.",
"restrictionInformationP1": "Rhaid i chi wirio a oes unrhyw gyfyngiadau riportio yn berthnasol cyn cyhoeddi manylion am unrhyw un o'r achosion a restrir yma, naill ai'n ysgrifenedig, mewn darllediad neu ar y rhyngrwyd, gan gynnwys y cyfryngau cymdeithasol.",
"restrictionInformationBoldText": "Byddwch yn euog o ddirmyg llys os byddwch yn cyhoeddi unrhyw wybodaeth sydd wedi'i diogelu gan gyfyngiad riportio. Gallwch gael dirwy, eich dedfrydu i garchar, neu'r ddau.",
"restrictionInformationP2": "Bydd cyfyngiadau penodol a orchmynnir gan y llys yn cael eu crybwyll ar yr achosion a restrir yma.",
"restrictionInformationP3": "Fodd bynnag, nid yw'r cyfyngiadau bob amser yn cael eu rhestru. Mae rhai yn berthnasol yn awtomatig. Er enghraifft, anhysbysrwydd a roddir i ddioddefwyr rhai troseddau rhywiol.",
"restrictionInformationP4": "I ganfod pa gyfyngiadau riportio sy'n berthnasol ar achos penodol, cysylltwch â'r:",
"restrictionBulletPoint1": "llys yn uniongyrchol",
"restrictionBulletPoint2": "Gwasanaeth Llysoedd a Thribiwnlysoedd EM ar 0330 808 4407",
"courtRoom": "Ystafell llys",
"sittingAt": "Yn eistedd yn",
"tableHeaders": [
"Cyfeirnod yr Achos",
"Enw'r Diffynnydd(Diffynyddion)",
"Math o Wrandawiad",
"Cynrychiolir gan",
"Yr Awdurdod sy'n Erlyn",
"Nodiadau Rhestru"
],
"dataSource": "Ffynhonnell Data"
}
28 changes: 28 additions & 0 deletions src/main/resources/locales/en/crown-firm-pdda-list.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
{
"title": "Crown Firm List",
"heading": "Crown Firm List for",
"listDate": "List for",
"to": "to",
"listUpdated": "Last updated",
"at": "at",
"versionText": "Version",
"restrictionInformationHeading": "Restrictions on publishing or writing about these cases",
"restrictionInformationP1": "You must check if any reporting restrictions apply before publishing details on any of the cases listed here either in writing, in a broadcast or by internet, including social media.",
"restrictionInformationBoldText": "You'll be in contempt of court if you publish any information which is protected by a reporting restriction. You could get a fine, prison sentence or both.",
"restrictionInformationP2": "Specific restrictions ordered by the court will be mentioned on the cases listed here.",
"restrictionInformationP3": "However, restrictions are not always listed. Some apply automatically. For example, anonymity given to the victims of certain sexual offences.",
"restrictionInformationP4": "To find out which reporting restrictions apply on a specific case, contact:",
"restrictionBulletPoint1": "the court directly",
"restrictionBulletPoint2": "HM Courts and Tribunals Service on 0330 808 4407",
"courtRoom": "Courtroom",
"sittingAt": "Sitting at",
"tableHeaders": [
"Case Number",
"Defendant Name(s)",
"Hearing Type",
"Representative",
"Prosecuting Authority",
"Listing Notes"
],
"dataSource": "Data Source"
}
1 change: 1 addition & 0 deletions src/main/routes/routes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -212,6 +212,7 @@ export default function (app: Application): void {
'magistrates-adult-court-list-future'
)
);
app.get('/crown-firm-pdda-list', app.locals.container.cradle.crownFirmPddaListController.get);

//Non-Strategic Paths
app.get('/cst-weekly-hearing-list', (req, res) =>
Expand Down
134 changes: 134 additions & 0 deletions src/main/service/listManipulation/CrownFirmPddaListService.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
import { ListParseHelperService } from '../ListParseHelperService';
import { formatDate } from '../../helpers/dateTimeHelper';

const helperService = new ListParseHelperService();

export class CrownFirmPddaListService {
public processPayload(payload: JSON, language: string): any[] {
const results = [];
payload['FirmList'].CourtLists.forEach(courtList => {
const courtHouse = courtList.CourtHouse;
results.push({
sittingDate: formatDate(this.toIsoDate(courtList.SittingDate), 'EEEE dd MMMM yyyy', language),
courtName: courtHouse.CourtHouseName,
courtAddress: courtHouse.CourtHouseAddress ? this.formatAddress(courtHouse.CourtHouseAddress) : [],
courtPhone: courtHouse.CourtHouseTelephone ? courtHouse.CourtHouseTelephone : '',
sittings: this.buildSittingInfo(courtList),
});
});
return results;
}

private buildSittingInfo(courtList: any): any[] {
const sittings = [];
courtList.Sittings.forEach(sitting => {
sittings.push({
courtRoomNumber: sitting.CourtRoomNumber,
sittingAt: sitting.SittingAt ? helperService.publicationTimeInUkTime(sitting.SittingAt) : '',
judgeName: this.formatJudgeName(sitting.Judiciary),
hearings: this.buildHearings(sitting),
});
});
return sittings;
}

private buildHearings(sitting: any): any[] {
const hearings = [];
sitting.Hearings.forEach(hearing => {
hearings.push({
caseNumber: hearing.CaseNumberCaTH,
defendantName: hearing.Defendants ? this.formatDefendantName(hearing.Defendants) : '',
hearingType: hearing.HearingDetails.HearingDescription,
representativeName: hearing.Defendants ? this.formatRepresentativeName(hearing.Defendants) : '',
prosecutingAuthority: hearing.Prosecution?.ProsecutingAuthority
? hearing.Prosecution.ProsecutingAuthority
: '',
listNote: hearing.ListNote ? hearing.ListNote : '',
});
});
return hearings;
}

private formatJudgeName(judiciary): string {
const names = [];
names.push(this.formatIndividualName(judiciary.Judge));

if (judiciary.Justice) {
judiciary.Justice.forEach(justice => {
names.push(this.formatIndividualName(justice));
});
}
return names.filter(name => name.trim().length > 0).join(', ');
}

private formatDefendantName(defendants): string {
const names = [];
defendants.forEach(defendant => {
names.push(this.useMaskedNameIfRequested(defendant.PersonalDetails));
});
return names.filter(name => name.trim().length > 0).join(', ');
}

private formatRepresentativeName(defendants): string {
const names = [];
defendants.forEach(defendant => {
defendant.Counsel?.forEach(counsel =>
counsel.Solicitor?.forEach(solicitor => {
const party = solicitor.Party;
if (party?.Person) {
names.push(this.useMaskedNameIfRequested(party.Person.PersonalDetails));
} else if (party?.Organisation) {
names.push(party.Organisation.OrganisationName);
}
})
);
});
return names.filter(name => name.trim().length > 0).join(', ');
}

private useMaskedNameIfRequested(nameDetails): string {
if (nameDetails.IsMasked && nameDetails.IsMasked == 'YES') {
return nameDetails.MaskedName ? nameDetails.MaskedName : '';
}
return this.formatIndividualName(nameDetails.Name);
}

private formatIndividualName(individual): string {
return individual.CitizenNameRequestedName
? individual.CitizenNameRequestedName
: this.formatNameParts(individual);
}

private formatNameParts(individual): string {
const nameParts = [];
if (individual.CitizenNameTitle) {
nameParts.push(individual.CitizenNameTitle);
}
if (individual.CitizenNameForename) {
nameParts.push(individual.CitizenNameForename);
}
if (individual.CitizenNameSurname) {
nameParts.push(individual.CitizenNameSurname);
}
if (individual.CitizenNameSuffix) {
nameParts.push(individual.CitizenNameSuffix);
}
return nameParts.filter(part => part.trim().length > 0).join(' ');
}

public formatAddress(address): string[] {
const addressLines = [];
if (address) {
address.Line.forEach(line => addressLines.push(line));
if (address.Postcode) {
addressLines.push(address.Postcode);
}
}
return addressLines.filter(line => line.trim().length > 0);
}

public toIsoDate(date: string): string {
const dateParts = date.split('-');
return new Date(Number(dateParts[0]), Number(dateParts[1]) - 1, Number(dateParts[2])).toISOString();
}
}
Loading
Loading