Skip to content

Commit

Permalink
feat(effective submission date): Set Initial Submission Date to the n…
Browse files Browse the repository at this point in the history
…ext valid business day. (#358)

* functional

* Add tests

* remove unneeded info

* remove throw

* Correct logic

* Naming

* accommodate github

* Update per paul's comments
  • Loading branch information
mdial89f authored Feb 5, 2024
1 parent e5f26ea commit d5c9e6a
Show file tree
Hide file tree
Showing 5 changed files with 93 additions and 4 deletions.
8 changes: 7 additions & 1 deletion src/packages/shared-utils/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,5 +3,11 @@
"version": "0.0.0",
"private": true,
"license": "MIT",
"devDependencies": {}
"scripts": {
"test": "vitest"
},
"devDependencies": {},
"dependencies": {
"@18f/us-federal-holidays": "^4.0.0"
}
}
26 changes: 26 additions & 0 deletions src/packages/shared-utils/seatool-date-helper.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import moment from "moment-timezone";
import * as fedHolidays from '@18f/us-federal-holidays';


// This manually accounts for the offset between the client's timezone and UTC.
export const offsetForUtc = (date: Date): Date => {
Expand All @@ -18,4 +20,28 @@ export const seaToolFriendlyTimestamp = (date?: Date): number => {
// This takes an epoch string and converts it to a standard format for display
export const formatSeatoolDate = (date: string): string => {
return moment(date).tz("UTC").format("MM/DD/yyyy")
}

export const getNextBusinessDayTimestamp = (date: Date = new Date()): number => {
let localeStringDate = date.toLocaleString("en-US", { timeZone: "America/New_York", dateStyle: "short" });
let localeStringHours24 = date.toLocaleString("en-US", { timeZone: "America/New_York", hour: 'numeric', hour12: false });
let localeDate = new Date(localeStringDate);

console.log(`Evaluating ${localeStringDate} at ${localeStringHours24}`);

const after5pmEST = parseInt(localeStringHours24,10) >= 17
const isHoliday = fedHolidays.isAHoliday(localeDate)
const isWeekend = !(localeDate.getDay() % 6)
if(after5pmEST || isHoliday || isWeekend) {
let nextDate = localeDate;
nextDate.setDate(nextDate.getDate() + 1);
nextDate.setHours(12,0,0,0)
console.log("Current date is not valid. Will try " + nextDate)
return getNextBusinessDayTimestamp(nextDate)
}

// Return the next business day's epoch for midnight UTC
let ret = offsetForUtc(localeDate).getTime();
console.log('Current date is a valid business date. Will return ' + ret);
return ret;
}
42 changes: 42 additions & 0 deletions src/packages/shared-utils/tests/seatool-date-helper.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import { it, describe, expect } from "vitest";
import { getNextBusinessDayTimestamp } from "../seatool-date-helper";

describe("The getNextBusinessDayTimestamp function", () => {
it("identifies weekenends", () => {
let testDate = new Date(2024, 0, 27, 12, 0, 0); // Saturday, noon, utc
let nextDate = getNextBusinessDayTimestamp(testDate);
expect(nextDate).toEqual(Date.UTC(2024, 0, 29)); // Monday, midnight, utc
});

it("identifies holidays", () => {
let testDate = new Date(2024, 0, 15, 12, 0, 0); // MLK Day, a Monday
let nextDate = getNextBusinessDayTimestamp(testDate);
expect(nextDate).toEqual(Date.UTC(2024, 0, 16)); // Tuesday, midnight, utc
});

it("identifies submissions after 5pm eastern", () => {
let testDate = new Date(2024, 0, 17, 23, 0, 0); // Wednesday 11pm utc, Wednesday 6pm eastern
let nextDate = getNextBusinessDayTimestamp(testDate);
expect(nextDate).toEqual(Date.UTC(2024, 0, 18)); // Thursday, midnight, utc
});

it("identifies submissions before 5pm eastern", () => {
let testDate = new Date(2024, 0, 17, 10, 0, 0); // Wednesday 10am utc, Wednesday 5am eastern
let nextDate = getNextBusinessDayTimestamp(testDate);
expect(nextDate).toEqual(Date.UTC(2024, 0, 17)); // Wednesday, midnight, utc
});

it("handles combinations of rule violations", () => {
let testDate = new Date(2024, 0, 12, 23, 0, 0); // Friday 11pm utc, Friday 6pm eastern
let nextDate = getNextBusinessDayTimestamp(testDate);
// Submission is after 5pm, Saturday is a weekend, Sunday is a weekend, and Monday is MLK Day
expect(nextDate).toEqual(Date.UTC(2024, 0, 16)); // Tuesday, midnight utc
});

it("identifies valid business days", () => {
let testDate = new Date(2024, 0, 9, 15, 0, 0); // Tuesday 3pm utc, Tuesday 8am eastern
let nextDate = getNextBusinessDayTimestamp(testDate);
expect(nextDate).toEqual(Date.UTC(2024, 0, 9)); // Tuesday, midnight utc
});

});
12 changes: 10 additions & 2 deletions src/services/api/handlers/submit.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,10 @@ const config = {

import { Kafka, Message } from "kafkajs";
import { PlanType, onemacSchema, transformOnemac } from "shared-types";
import { seaToolFriendlyTimestamp } from "shared-utils";
import {
getNextBusinessDayTimestamp,
seaToolFriendlyTimestamp,
} from "shared-utils";
import { buildStatusMemoQuery } from "../libs/statusMemo";

const kafka = new Kafka({
Expand Down Expand Up @@ -63,6 +66,11 @@ export const submit = async (event: APIGatewayEvent) => {
}

const today = seaToolFriendlyTimestamp();
const submissionDate = getNextBusinessDayTimestamp();
console.log(
"Initial Submission Date determined to be: " +
new Date(submissionDate).toISOString()
);
const pool = await sql.connect(config);
console.log(body);
const query = `
Expand All @@ -71,7 +79,7 @@ export const submit = async (event: APIGatewayEvent) => {
,'${body.state}'
,(Select Region_ID from SEA.dbo.States where State_Code = '${body.state}')
,(Select Plan_Type_ID from SEA.dbo.Plan_Types where Plan_Type_Name = '${body.authority}')
,dateadd(s, convert(int, left(${today}, 10)), cast('19700101' as datetime))
,dateadd(s, convert(int, left(${submissionDate}, 10)), cast('19700101' as datetime))
,dateadd(s, convert(int, left(${today}, 10)), cast('19700101' as datetime))
,dateadd(s, convert(int, left(${body.proposedEffectiveDate}, 10)), cast('19700101' as datetime))
,(Select SPW_Status_ID from SEA.dbo.SPW_Status where SPW_Status_DESC = 'Pending')
Expand Down
9 changes: 8 additions & 1 deletion yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,13 @@
d "1"
es5-ext "^0.10.47"

"@18f/us-federal-holidays@^4.0.0":
version "4.0.0"
resolved "https://registry.yarnpkg.com/@18f/us-federal-holidays/-/us-federal-holidays-4.0.0.tgz#1c0c2963ffd3f52b7527ff8e3cd1ecc89b48533d"
integrity sha512-93eCrGIE8lZZvMByJz1Me76e4RIEuMq3n2Tn5yYgnXFB5ZhoLVe2/tWGnE+7VpRA6X1lPDln5YgChClIFP6kPA==
dependencies:
dayjs "^1.10.6"

"@aashutoshrathi/word-wrap@^1.2.3":
version "1.2.6"
resolved "https://registry.yarnpkg.com/@aashutoshrathi/word-wrap/-/word-wrap-1.2.6.tgz#bd9154aec9983f77b3a034ecaa015c2e4201f6cf"
Expand Down Expand Up @@ -8918,7 +8925,7 @@ dateformat@^3.0.0:
resolved "https://registry.yarnpkg.com/dateformat/-/dateformat-3.0.3.tgz#a6e37499a4d9a9cf85ef5872044d62901c9889ae"
integrity sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==

dayjs@^1.11.8:
dayjs@^1.10.6, dayjs@^1.11.8:
version "1.11.10"
resolved "https://registry.yarnpkg.com/dayjs/-/dayjs-1.11.10.tgz#68acea85317a6e164457d6d6947564029a6a16a0"
integrity sha512-vjAczensTgRcqDERK0SR2XMwsF/tSvnvlv6VcF2GIhg6Sx4yOIt/irsr1RDJsKiIyBzJDpCoXiWWq28MqH2cnQ==
Expand Down

0 comments on commit d5c9e6a

Please sign in to comment.