Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Reprocessed Modal: Submission History #3343

Merged
merged 15 commits into from
Dec 17, 2024
14 changes: 14 additions & 0 deletions tdrs-frontend/src/assets/Reports.scss
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,20 @@
cursor: pointer;
}

.reprocessed {
background-color: transparent;
border: none;
color: #264A64;
text-align: left;
text-decoration: underline;
margin: 0;
padding: 0;
}

.reprocessed:hover {
cursor: pointer;
}

.usa-table caption {
width: 100%;
}
10 changes: 4 additions & 6 deletions tdrs-frontend/src/components/Modal/Modal.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,18 +24,17 @@ const Modal = ({ title, message, buttons = [], isVisible = false }) => {
(b) => b.key === selectedButtonKey
)

const btnIdxMinOne = Math.max(0, buttons.length - 1)
if (shiftKey) {
// go backward
const selectedIdxMinOne = Math.max(0, selectedButtonIndex - 1)
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This fixed a bug where we could get an array out of bounds error. We could also escape the modal with tabs when this error occurred.

nextButtonIndex =
selectedButtonIndex >= 0
? selectedButtonIndex - 1
: buttons.length - 1
selectedButtonIndex >= 0 ? selectedIdxMinOne : btnIdxMinOne
} else {
nextButtonIndex =
selectedButtonIndex < buttons.length - 1 ? selectedButtonIndex + 1 : 0
selectedButtonIndex < btnIdxMinOne ? selectedButtonIndex + 1 : 0
}
}

const nextButtonKey = buttons[nextButtonIndex].key
const nextButton = modalRef.current.querySelector(
`button[buttonkey="${nextButtonKey}"]`
Expand All @@ -45,7 +44,6 @@ const Modal = ({ title, message, buttons = [], isVisible = false }) => {

const onKeyDown = (e) => {
const { key, shiftKey } = e

switch (key) {
case 'Tab':
onTabPressed(shiftKey)
Expand Down
13 changes: 13 additions & 0 deletions tdrs-frontend/src/components/Reports/Reports.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import { fetchSttList } from '../../actions/sttList'
import Modal from '../Modal'
import SegmentedControl from '../SegmentedControl'
import SubmissionHistory from '../SubmissionHistory'
import ReprocessedModal from '../SubmissionHistory/ReprocessedModal'
import { selectPrimaryUserRole } from '../../selectors/auth'

/**
Expand Down Expand Up @@ -55,6 +56,9 @@ function Reports() {
const [formValidation, setFormValidationState] = useState({})
const [touched, setTouched] = useState({})

const [reprocessedModalVisible, setReprocessedModalVisible] = useState(false)
const [reprocessedDate, setReprocessedDate] = useState('')

const quarters = {
Q1: 'Quarter 1 (October - December)',
Q2: 'Quarter 2 (January - March)',
Expand Down Expand Up @@ -472,6 +476,10 @@ function Reports() {
stt: stt,
file_type: fileTypeInputValue,
}}
reprocessedState={{
setModalVisible: setReprocessedModalVisible,
setDate: setReprocessedDate,
}}
/>
)}
</>
Expand Down Expand Up @@ -499,6 +507,11 @@ function Reports() {
},
]}
/>
<ReprocessedModal
date={reprocessedDate}
isVisible={reprocessedModalVisible}
setModalVisible={setReprocessedModalVisible}
/>
</>
)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import {
downloadFile,
getErrorReportStatus,
} from './helpers'
import { ReprocessedButton } from './ReprocessedModal'

const MonthSubRow = ({ data }) =>
data ? (
Expand All @@ -24,15 +25,20 @@ const MonthSubRow = ({ data }) =>
</>
)

const CaseAggregatesRow = ({ file }) => {
const CaseAggregatesRow = ({ file, reprocessedState }) => {
const dispatch = useDispatch()

const reprocessedDate = formatDate(getReprocessedDate(file))
return (
<>
<tr>
<th scope="rowgroup" rowSpan={3}>
{formatDate(file.createdAt) + ' by ' + file.submittedBy}
{hasReparsed(file) && <></>}
{hasReparsed(file) && (
<ReprocessedButton
date={reprocessedDate}
reprocessedState={reprocessedState}
/>
)}
</th>

<th scope="rowgroup" rowSpan={3}>
Expand Down Expand Up @@ -75,7 +81,7 @@ const CaseAggregatesRow = ({ file }) => {
)
}

export const CaseAggregatesTable = ({ files }) => (
export const CaseAggregatesTable = ({ files, reprocessedState }) => (
<>
<thead>
<tr>
Expand Down Expand Up @@ -107,7 +113,11 @@ export const CaseAggregatesTable = ({ files }) => (
</thead>
<tbody>
{files.map((file) => (
<CaseAggregatesRow key={file.id} file={file} />
<CaseAggregatesRow
key={file.id}
file={file}
reprocessedState={reprocessedState}
/>
))}
</tbody>
</>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
import React, { useState } from 'react'
import Modal from '../Modal'

const Message = ({ date }) => {
return (
<>
We've reprocessed your submission with updated validation criteria, based
on system improvements, to improve accuracy of error reports. No changes
have been made to your original data submission.
<br />
<br />
Data was reprocessed on: {date}
</>
)
}

export const ReprocessedButton = ({ date, reprocessedState }) => {
return (
<div>
<button
className="reprocessed"
onClick={() => {
reprocessedState.setDate(date)
reprocessedState.setModalVisible(true)
}}
>
Reprocessed &#9432;
</button>
</div>
)
}

const ReprocessedModal = ({ date, isVisible, setModalVisible }) => {
const message = <Message date={date} />
return (
<Modal
title="Most Recent Reprocessed Date"
message={message}
isVisible={isVisible}
buttons={[
{
key: '1',
text: 'Close',
onClick: () => {
setModalVisible(false)
},
},
]}
/>
)
}

export default ReprocessedModal
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,12 @@ import { useState } from 'react'
import { CaseAggregatesTable } from './CaseAggregatesTable'
import { TotalAggregatesTable } from './TotalAggregatesTable'

const SectionSubmissionHistory = ({ section, label, files }) => {
const SectionSubmissionHistory = ({
section,
label,
files,
reprocessedState,
}) => {
const pageSize = 5
const [resultsPage, setResultsPage] = useState(1)

Expand All @@ -30,7 +35,10 @@ const SectionSubmissionHistory = ({ section, label, files }) => {
<table className="usa-table usa-table--striped">
<caption>{`Section ${section} - ${label}`}</caption>
{files && files.length > 0 ? (
<TableComponent files={files.slice(pageStart, pageEnd)} />
<TableComponent
files={files.slice(pageStart, pageEnd)}
reprocessedState={reprocessedState}
/>
) : (
<span>No data available.</span>
)}
Expand All @@ -57,9 +65,13 @@ SectionSubmissionHistory.propTypes = {
year: PropTypes.string,
}),
files: PropTypes.array,
reprocessedState: PropTypes.shape({
setModalVisible: PropTypes.func,
setDate: PropTypes.func,
}),
}

const SubmissionHistory = ({ filterValues }) => {
const SubmissionHistory = ({ filterValues, reprocessedState }) => {
const dispatch = useDispatch()
const [hasFetchedFiles, setHasFetchedFiles] = useState(false)
const { files } = useSelector((state) => state.reports)
Expand Down Expand Up @@ -95,6 +107,7 @@ const SubmissionHistory = ({ filterValues }) => {
label={section}
filterValues={filterValues}
files={files.filter((f) => f.section.includes(section))}
reprocessedState={reprocessedState}
/>
)
})}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,10 +22,22 @@ describe('SubmissionHistory', () => {
file_type: 'TANF',
}

const setup = (store = appStore, filterValues = defaultFilterValues) =>
const defaultReprocessedState = {
setDate: () => {},
setModalVisible: () => {},
}

const setup = (
store = appStore,
filterValues = defaultFilterValues,
reprocessedState = defaultReprocessedState
) =>
render(
<Provider store={store}>
<SubmissionHistory filterValues={filterValues} />
<SubmissionHistory
filterValues={filterValues}
reprocessedState={reprocessedState}
/>
</Provider>
)

Expand Down Expand Up @@ -474,4 +486,42 @@ describe('SubmissionHistory', () => {
}
}
)

it('Shows Reprocessed button', () => {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@elipe17 do we need more tests here to capture the following scenarios:

  • reprocessing tribal TANF file
  • reprocessing SSP file
  • no reprocessing

Asking because I noticed that reprocessing indicators are not appearing for tribal TANF and SSP files. evidence below.

Screenshot 2024-12-16 124333
Screenshot 2024-12-16 123500

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It should be the same exact logic regardless of TANF, SSP, Tribal. I just tested SSP locally and it was fine. Let me checkout the deployed env

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@ADPennington I just tested in the Raft env since it is still deployed there and it is working as expected for TANF, SSP, and Tribal. Maybe we can deploy this back to qasp when you are ready and check it out together?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thank you @elipe17 -- one thing i forgot to mention is that I was testing aggregate and stratum files for SSP and tribal TANF.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Roger. I tested active, closed, and aggregate for TANF. Active and aggregate for SPP. Only active for Tribal. Let me know when you are ready to test it out and we can hop on a call or work async via the deployment

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@elipe17 re-deploying now

const state = {
reports: {
files: [
{
id: '123',
fileName: 'test1.txt',
fileType: 'TANF',
quarter: 'Q1',
section: 'Active Case Data',
uuid: '123-4-4-321',
year: '2023',
s3_version_id: '321-0-0-123',
createdAt: '12/12/2012 12:12',
submittedBy: '[email protected]',
latest_reparse_file_meta: {
finished: true,
success: true,
started_at: '2024-12-09T18:38:14+0000',
finished_at: '2024-12-09T18:38:16+0000',
},
},
],
},
}

const store = appConfigureStore(state)
const dispatch = jest.fn(store.dispatch)
store.dispatch = dispatch

setup(store)

expect(screen.queryByText('test1.txt')).toBeInTheDocument()

const reprocessedBtn = screen.queryByText('Reprocessed ⓘ')
expect(reprocessedBtn).toBeInTheDocument()
})
})
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import {
downloadFile,
getErrorReportStatus,
} from './helpers'
import { ReprocessedButton } from './ReprocessedModal'

const MonthSubRow = ({ data }) =>
data ? (
Expand All @@ -22,15 +23,20 @@ const MonthSubRow = ({ data }) =>
</>
)

const TotalAggregatesRow = ({ file }) => {
const TotalAggregatesRow = ({ file, reprocessedState }) => {
const dispatch = useDispatch()

const reprocessedDate = formatDate(getReprocessedDate(file))
return (
<>
<tr>
<th scope="rowgroup" rowSpan={3}>
{formatDate(file.createdAt) + ' by ' + file.submittedBy}
{hasReparsed(file) && <></>}
{hasReparsed(file) && (
<ReprocessedButton
date={reprocessedDate}
reprocessedState={reprocessedState}
/>
)}
</th>

<th scope="rowgroup" rowSpan={3}>
Expand Down Expand Up @@ -69,7 +75,7 @@ const TotalAggregatesRow = ({ file }) => {
)
}

export const TotalAggregatesTable = ({ files }) => (
export const TotalAggregatesTable = ({ files, reprocessedState }) => (
<>
<thead>
<tr>
Expand All @@ -95,7 +101,11 @@ export const TotalAggregatesTable = ({ files }) => (
</thead>
<tbody>
{files.map((file) => (
<TotalAggregatesRow key={file.id} file={file} />
<TotalAggregatesRow
key={file.id}
file={file}
reprocessedState={reprocessedState}
/>
))}
</tbody>
</>
Expand Down
3 changes: 2 additions & 1 deletion tdrs-frontend/src/components/SubmissionHistory/helpers.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,8 @@ export const hasReparsed = (f) =>
f.latest_reparse_file_meta.finished_at &&
f.latest_reparse_file_meta.finished_at !== null

export const getReprocessedDate = (f) => f.latest_reparse_file_meta.finished_at
export const getReprocessedDate = (f) =>
f?.latest_reparse_file_meta?.finished_at

export const getErrorReportStatus = (file) => {
if (
Expand Down
Loading