diff --git a/actions/selectQueryTypes.js b/actions/selectQueryTypes.js index d80c2291..b635f864 100644 --- a/actions/selectQueryTypes.js +++ b/actions/selectQueryTypes.js @@ -82,7 +82,7 @@ export const getSelectQuery = (appealTypeName) => { return "&$select=pinswg_eiarequired,pinswg_anticipatedgridreferenceeastingtext,pinswg_anticipatedgridreferencenorthingtext,_pinswg_appellant_value,pinswg_name,pinswg_addressline1,pinswg_addressline2,pinswg_postcode,pinswg_addresstown,_pinswg_associatedlpa_value,pinswg_addresscounty,pinswg_applicationacceptedasvalid,pinswg_applicationrejectedasinvalid,pinswg_choiceofprocedure,pinswg_confirmrequesttovaryapplication,pinswg_dateeventrequested,pinswg_dateofdecision,pinswg_dateofrequesttovarytheapplication,pinswg_dateofsubmissionofapplication,pinswg_dateprojectpublishedonwebsite,pinswg_deadlineforsubmissionofapplication,pinswg_endofrepresentationperiod,pinswg_inspectorreportsubmittedtowelshgovernment,pinswg_procedureconfirmed,pinswg_projectdescription,pinswg_projectlocation,pinswg_recommendation,pinswg_rejectrequesttovaryapplication,pinswg_reportdueby,pinswg_suspensiondates,pinswg_suspensionenddates,pinswg_suspensionstartdate,pinswg_validnoticeofintentiontosubmitanapplicati,pinswg_webaddress,pinswg_withdrawndate,pinswg_writtenacceptanceofnotification,statuscode,pinswg_casestage,pinswg_startdateofevent,pinswg_typeofevent"; case "pinswg_sipses": // return "&$select=pinswg_anticipatedgridreferenceeastingtext,pinswg_anticipatedgridreferencenorthingtext,_pinswg_appellant_value,pinswg_name,pinswg_addressline1,pinswg_addressline2,pinswg_postcode,pinswg_addresstown,_pinswg_associatedlpa_value,pinswg_addresscounty,pinswg_applicationacceptedasvalid,pinswg_applicationrejectedasinvalid,pinswg_choiceofprocedure,pinswg_confirmrequesttovaryapplication,pinswg_dateeventrequested,pinswg_dateofdecision,pinswg_dateofrequesttovarytheapplication,pinswg_dateofsubmissionofapplication,pinswg_dateprojectpublishedonwebsite,pinswg_deadlineforsubmissionofapplication,pinswg_decision,pinswg_endofrepresentationperiod,pinswg_inspectorreportsubmittedtowelshgovernment,pinswg_procedureconfirmed,pinswg_projectdescription,pinswg_projectlocation,pinswg_recommendation,pinswg_rejectrequesttovaryapplication,pinswg_reportdueby,pinswg_suspensiondates,pinswg_suspensionenddates,pinswg_suspensionstartdates,pinswg_validnoticeofintentiontosubmitanapplicati,pinswg_webaddress,pinswg_withdrawndate,pinswg_writtenacceptanceofnotification,statuscode,pinswg_casestage,_pinswg_dnsids_value,pinswg_startdateofevent,pinswg_typeofevent"; - return "&$select=_pinswg_projecttype_value,pinswg_eiarequired,pinswg_anticipatedgridrefeasting,pinswg_anticipatedgridrefnorthing,_pinswg_appellant_value,pinswg_name,_pinswg_associatedlpa_value,pinswg_choiceofprocedure,pinswg_decision,pinswg_projectdescription,pinswg_projectlocation,pinswg_recommendation,statuscode,pinswg_casestage,_pinswg_sipscase_value,pinswg_writtenacceptanceofnotification,pinswg_validnoticeofintentiontosubmit,pinswg_deadlineforsubmissionofapplication,pinswg_screeningstartdate,pinswg_eiatargetdate,pinswg_targetextended,pinswg_directionissueddate,pinswg_eiarequired,pinswg_scopingstartdate,pinswg_scopingtargetdate,pinswg_scopingtargetextended,pinswg_scopingoutcomeissueddate,pinswg_essubmitted,pinswg_deemedmarinelicenseappliedfor,pinswg_validationdeadlineextension,pinswg_consultationopen,pinswg_consultationclose,pinswg_reportissuedtowelshministers,pinswg_decisionissuedtoapplicant,pinswg_decisionoutcome,pinswg_redetermination,pinswg_redeterminationconsultationdeadline"; + return "&$select=pinswg_casedeadline,_pinswg_projecttype_value,pinswg_eiarequired,pinswg_anticipatedgridrefeasting,pinswg_anticipatedgridrefnorthing,_pinswg_appellant_value,pinswg_name,_pinswg_associatedlpa_value,pinswg_choiceofprocedure,pinswg_decision,pinswg_projectdescription,pinswg_projectlocation,pinswg_recommendation,statuscode,pinswg_casestage,_pinswg_sipscase_value,pinswg_writtenacceptanceofnotification,pinswg_validnoticeofintentiontosubmit,pinswg_deadlineforsubmissionofapplication,pinswg_screeningstartdate,pinswg_eiatargetdate,pinswg_targetextended,pinswg_directionissueddate,pinswg_eiarequired,pinswg_scopingstartdate,pinswg_scopingtargetdate,pinswg_scopingtargetextended,pinswg_scopingoutcomeissueddate,pinswg_essubmitted,pinswg_deemedmarinelicenseappliedfor,pinswg_validationdeadlineextension,pinswg_consultationopen,pinswg_consultationclose,pinswg_reportissuedtowelshministers,pinswg_decisionissuedtoapplicant,pinswg_decisionoutcome,pinswg_redetermination,pinswg_redeterminationconsultationdeadline"; break; default: return ""; diff --git a/components/case/events.js b/components/case/events.js index 6867d3dd..1b438d3b 100644 --- a/components/case/events.js +++ b/components/case/events.js @@ -222,7 +222,9 @@ const EventsDetails = (props) => { target="_blank" rel="noopener noreferrer" > - Watch live stream + {t( + "case:live-event-link" + )} )} diff --git a/components/case/summary.js b/components/case/summary.js index 02548408..a2016bdf 100644 --- a/components/case/summary.js +++ b/components/case/summary.js @@ -379,12 +379,12 @@ const CaseSummary = (props) => { className="govuk-notification-banner__title" id="live-event-title" > - Live event + {t("case:live-event-subheading")}

- A live streamed event is happening now. + {t("case:live-event-copy")}

{livePublishedEvent.pinswg_eventname && ( @@ -401,7 +401,7 @@ const CaseSummary = (props) => { target="_blank" rel="noopener noreferrer" > - Watch live stream + {t("case:live-event-link")}
diff --git a/components/case/summaryTypes/pinswg_sipscase.js b/components/case/summaryTypes/pinswg_sipscase.js index a8f8eba3..f837b525 100644 --- a/components/case/summaryTypes/pinswg_sipscase.js +++ b/components/case/summaryTypes/pinswg_sipscase.js @@ -29,6 +29,17 @@ const Pinswg_sipscase = (props) => { ); } + const extensions = + detailsObj.pinswg_CaseDeadlineExtension_pinswg_sips || []; + + const latest = extensions.sort( + (a, b) => + new Date(b.pinswg_datedeadlineextended) - + new Date(a.pinswg_datedeadlineextended) + )[0]; + + console.log(latest); + return ( <> {detailsObj.pinswg_projectdescription != null ? ( @@ -485,7 +496,48 @@ const Pinswg_sipscase = (props) => {

{t("case:summary-dates-label")}

-

+
+ { + const fallback = t( + "case:summary-awaiting-information-label" + ); + + const extensions = + detailsObj.pinswg_CaseDeadlineExtension_pinswg_sips || + []; + + const latestExtension = + extensions + .filter( + (extension) => + !_.isEmpty( + extension.pinswg_datedeadlineextended + ) + ) + .sort( + (a, b) => + new Date( + b.pinswg_datedeadlineextended + ) - + new Date( + a.pinswg_datedeadlineextended + ) + )[0]; + + const dateToDisplay = + latestExtension + ? latestExtension.pinswg_datedeadlineextended + : detailsObj.pinswg_casedeadline; + + return !_.isEmpty(dateToDisplay) + ? formatDates(dateToDisplay) + : fallback; + })()} + /> +
+

{t( "case:summary-pre-submission-sub-title" )} diff --git a/components/search/addresssearchresults.js b/components/search/addresssearchresults.js index bf3b05bb..f980c090 100644 --- a/components/search/addresssearchresults.js +++ b/components/search/addresssearchresults.js @@ -30,6 +30,7 @@ import { getWatchedCasesProxy } from "../../actions/services/portalService"; import RepsOnResults from "./repsonresults"; +import LiveLink from "./liveLink"; const escapeRegExp = (string) => string.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"); @@ -394,6 +395,12 @@ const SearchResults = (props) => { +
diff --git a/components/search/dnssearchresults.js b/components/search/dnssearchresults.js index f68cd25d..40344b3c 100644 --- a/components/search/dnssearchresults.js +++ b/components/search/dnssearchresults.js @@ -8,6 +8,7 @@ import { connect } from "react-redux"; import transLookup from "../../data/lookuptranslations.json"; import PaginationControl from "./pagination"; import RepsOnResults from "./repsonresults"; +import LiveLink from "./liveLink"; import { getBasicDNSSearchPaged, @@ -468,6 +469,12 @@ const DNSSearchResults = (props) => { item.pinswg_appealcasetype } /> +
diff --git a/components/search/liveLink.js b/components/search/liveLink.js new file mode 100644 index 00000000..048db1cd --- /dev/null +++ b/components/search/liveLink.js @@ -0,0 +1,45 @@ +import Link from "next/link"; +import useTranslation from "next-translate/useTranslation"; + +const isSameDay = (dateA, dateB) => + dateA.getFullYear() === dateB.getFullYear() && + dateA.getMonth() === dateB.getMonth() && + dateA.getDate() === dateB.getDate(); + +const getLiveEvent = (detailsObj) => { + const events = detailsObj?.pinswg_sips_pinswg_sipsevent || []; + + if (!Array.isArray(events) || events.length === 0) return null; + + const now = new Date(); + + return events.find((event) => { + if (!event?.pinswg_dateeventrequested) return false; + + const eventDate = new Date(event.pinswg_dateeventrequested); + + return isSameDay(eventDate, now); + }); +}; + +const LiveLink = ({ detailsObj }) => { + let { t } = useTranslation(); + const liveEvent = getLiveEvent(detailsObj); + + if (!liveEvent || !liveEvent.pinswg_linktotheevent) return null; + + return ( + + ); +}; + +export default LiveLink; diff --git a/components/search/searchresults.js b/components/search/searchresults.js index fdb13543..4008f2f4 100644 --- a/components/search/searchresults.js +++ b/components/search/searchresults.js @@ -39,6 +39,7 @@ import { import { sendGAEvent } from "@next/third-parties/google"; import RepsOnResults from "./repsonresults"; +import LiveLink from "./liveLink"; import { query } from "jsonpath"; const escapeRegExp = (string) => string.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"); @@ -478,6 +479,12 @@ const SearchResults = (props) => { item.pinswg_appealcasetype } /> +
diff --git a/locales/cy/case.json b/locales/cy/case.json index 2fa6abf8..40a40edc 100644 --- a/locales/cy/case.json +++ b/locales/cy/case.json @@ -145,5 +145,8 @@ "summary-decision-issued-to-applicant": "Penderfyniad a Gyhoeddwyd i'r Ymgeisydd", "summary-decision-outcome": "Canlyniad y Penderfyniad", "media-title": "Recordiadau digwyddiadau", - "video-heading": "Fideos" + "video-heading": "Fideos", + "live-event-subheading": "Digwyddiad byw", + "live-event-copy": "Mae digwyddiad sy'n cael ei ffrydio'n fyw yn digwydd nawr.", + "live-event-link": "Gwylio'r ffrydio byw" } \ No newline at end of file diff --git a/locales/en/case.json b/locales/en/case.json index 0201f1cd..cb748277 100644 --- a/locales/en/case.json +++ b/locales/en/case.json @@ -146,5 +146,8 @@ "summary-decision-issued-to-applicant": "Decision Issued to Applicant", "summary-decision-outcome": "Decision Outcome", "media-title": "Event recordings", - "video-heading": "Videos" + "video-heading": "Videos", + "live-event-subheading": "Live event", + "live-event-copy": "A live streamed event is happening now.", + "live-event-link": "Watch live stream" } \ No newline at end of file diff --git a/pages/api/endpoint/getbasicsearchdetails_api.js b/pages/api/endpoint/getbasicsearchdetails_api.js index d77f340f..c1a3417d 100644 --- a/pages/api/endpoint/getbasicsearchdetails_api.js +++ b/pages/api/endpoint/getbasicsearchdetails_api.js @@ -86,7 +86,10 @@ export default async function ApiProxy(req, res) { "&$count=true" + "&$expand=" + navigationProperty + - "($select=ticketnumber)"; + "($select=ticketnumber)" + + (primaryIdAttribute == "pinswg_sipscase" + ? ",pinswg_CaseDeadlineExtension_pinswg_sips($select=pinswg_casedeadlineextensionid,pinswg_noofdaysextended,pinswg_reasonforextension,pinswg_agreedorimposedextension,pinswg_datedeadlineextended)" + : ""); queryUrl = queryUrl + getSelectQuery(appealTypeName); diff --git a/pages/api/endpoint/getbasicsearchdetailspaged_api.js b/pages/api/endpoint/getbasicsearchdetailspaged_api.js index c0ea5b18..532a70df 100644 --- a/pages/api/endpoint/getbasicsearchdetailspaged_api.js +++ b/pages/api/endpoint/getbasicsearchdetailspaged_api.js @@ -86,7 +86,10 @@ export default async function ApiProxy(req, res) { "&$count=true" + "&$expand=" + navigationProperty + - "($select=ticketnumber)"; + "($select=ticketnumber)" + + (primaryIdAttribute == "pinswg_sipscase" + ? ",pinswg_sipscase($select=ticketnumber),pinswg_CaseDeadlineExtension_pinswg_sips($select=pinswg_casedeadlineextensionid,pinswg_noofdaysextended,pinswg_reasonforextension,pinswg_agreedorimposedextension,pinswg_datedeadlineextended),pinswg_sips_pinswg_sipsevent($select=pinswg_linktotheevent,pinswg_name,pinswg_dateeventrequested,pinswg_typeofevent,createdon,modifiedon)" + : ""); queryUrl = queryUrl + @@ -137,7 +140,7 @@ export default async function ApiProxy(req, res) { if (_.has(data, "@odata.nextLink") === true) { const dataStr = JSON.stringify(data["@odata.nextLink"]); - data["@odata.nextLink"] = dataStr.split("/v8.2/")[1]; + data["@odata.nextLink"] = dataStr.split("/v9.2/")[1]; } return respondSuccess(res, data); diff --git a/pages/api/endpoint/getsipsdeadlineextensions_api.js b/pages/api/endpoint/getsipsdeadlineextensions_api.js new file mode 100644 index 00000000..5a33ede0 --- /dev/null +++ b/pages/api/endpoint/getsipsdeadlineextensions_api.js @@ -0,0 +1,29 @@ +import { respondError } from "../middleware/apiResponse"; +import { relayGet } from "../middleware/relayForwarding"; + +export default async function ApiProxy(req, res) { + const caseid = req.query.caseid; + + if (typeof caseid !== "string" || caseid.trim().length === 0) { + return respondError(res, { + status: 400, + code: "CASE_ID_REQUIRED", + message: "caseid is required" + }); + } + + const queryUrl = + "pinswg_casedeadlineextensions?$count=true&$filter=_pinswg_regardingcase_value eq " + + caseid + + " and pinswg_publishtoweb eq true&$select=pinswg_videoplatformurl,pinswg_eventrecordingid,pinswg_publishtoweb,pinswg_eventrecordingname,pinswg_eventrecordingpublisheddate,createdon"; + + return relayGet({ + queryUrl, + res, + errorResponse: { + status: 400, + code: "SIPS_MEDIA_FETCH_FAILED", + message: "Failed to fetch SIPS media" + } + }); +}