From 2ee41f8d8a83e8dcc2644a8d0954d71ca6d26321 Mon Sep 17 00:00:00 2001 From: raymond-hughes Date: Sun, 17 Sep 2023 22:49:00 -0400 Subject: [PATCH 01/20] Adding param for last appeal ID to appeals controller --- app/controllers/appeals_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/appeals_controller.rb b/app/controllers/appeals_controller.rb index da9b692039a..a2f752a284c 100644 --- a/app/controllers/appeals_controller.rb +++ b/app/controllers/appeals_controller.rb @@ -27,7 +27,7 @@ def index ).call else CaseSearchResultsForVeteranFileNumber.new( - file_number_or_ssn: case_search, user: current_user + file_number_or_ssn: case_search, user: current_user, last_id: params[:last_id] ).call end From 50f8365cc62fcd34ec155e7250f328e546047acc Mon Sep 17 00:00:00 2001 From: raymond-hughes Date: Sun, 17 Sep 2023 22:49:26 -0400 Subject: [PATCH 02/20] Adding limit and refactoring query to load smaller amount of appeals to avoid error --- app/services/appeal_finder.rb | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/app/services/appeal_finder.rb b/app/services/appeal_finder.rb index 30829666e7c..ca0be428d50 100644 --- a/app/services/appeal_finder.rb +++ b/app/services/appeal_finder.rb @@ -2,13 +2,21 @@ class AppealFinder class << self - def find_appeals_with_file_numbers(file_numbers) + def find_appeals_with_file_numbers(file_numbers, last_id = 0) return [] if file_numbers.empty? MetricsService.record("VACOLS: Get appeal information for file_numbers #{file_numbers}", service: :queue, name: "VeteranFinderQuery.find_appeals_with_file_numbers") do - appeals = Appeal.established.where(veteran_file_number: file_numbers).to_a + # limit set to 11 so we can determine if there is more to load + appeals = Appeal.established + .where(veteran_file_number: file_numbers).where(Appeal.arel_table[:id].gt(last_id)) + .includes(:decision_issues, :nod_date_updates, + :appellant_substitution, :hearings, + :request_issues, :work_mode, + :tasks, :available_hearing_locations, + :docket_switch, :remand_supplemental_claims) + .order(:id).limit(11).to_a begin appeals.concat(LegacyAppeal.fetch_appeals_by_file_number(*file_numbers)) rescue ActiveRecord::RecordNotFound From 67d47b7dbcd574c294f84ffa45dd14618114cfb7 Mon Sep 17 00:00:00 2001 From: raymond-hughes Date: Sun, 17 Sep 2023 22:50:13 -0400 Subject: [PATCH 03/20] Adding component for load more to search functions --- client/COPY.json | 1 + client/app/queue/CaseListLoadMore.jsx | 35 +++++++++++++++++++++++++++ client/app/queue/CaseListView.jsx | 3 ++- 3 files changed, 38 insertions(+), 1 deletion(-) create mode 100644 client/app/queue/CaseListLoadMore.jsx diff --git a/client/COPY.json b/client/COPY.json index 1a6b538883a..65fbc353db4 100644 --- a/client/COPY.json +++ b/client/COPY.json @@ -1,6 +1,7 @@ { "CASE_SEARCH_HOME_PAGE_HEADING": "Veteran Case Search", "CASE_SEARCH_INPUT_PLACEHOLDER": "Enter a file number, SSN, or AMA docket number", + "CASE_SEARCH_LOAD_MORE_TEXT": "Load More Cases", "CASE_SEARCH_INPUT_INSTRUCTION": "Please enter a valid claims file number, SSN, or AMA docket number (with hyphen) to search for all available cases.", "CASE_SEARCH_ERROR_EMPTY_SEARCH_TERM": "Cannot search for no text", "CASE_SEARCH_ERROR_INVALID_ID_HEADING": "Invalid search parameter ā€œ%sā€", diff --git a/client/app/queue/CaseListLoadMore.jsx b/client/app/queue/CaseListLoadMore.jsx new file mode 100644 index 00000000000..46d8743b6e1 --- /dev/null +++ b/client/app/queue/CaseListLoadMore.jsx @@ -0,0 +1,35 @@ +import React from 'react'; +import { connect } from 'react-redux'; +import { withRouter } from 'react-router-dom'; +import { bindActionCreators } from 'redux'; +import PropTypes from 'prop-types'; +import COPY from '../../COPY'; + +class CaseListLoadMore extends React.PureComponent { + render() { + return ( + + { COPY.CASE_SEARCH_LOAD_MORE_TEXT } + + ); + } +} + +CaseListLoadMore.propTypes = { + caseListCount: PropTypes.number +}; + +CaseListLoadMore.defaultProps = { + caseListCount: 0 +}; + +const mapDispatchToProps = (dispatch) => bindActionCreators({}, dispatch); + +const mapStateToProps = (state) => ({ caseList: state.caseList }); + +export default withRouter( + connect( + mapStateToProps, + mapDispatchToProps + )(CaseListLoadMore) +); diff --git a/client/app/queue/CaseListView.jsx b/client/app/queue/CaseListView.jsx index a01a23b83a4..85d596b98f2 100644 --- a/client/app/queue/CaseListView.jsx +++ b/client/app/queue/CaseListView.jsx @@ -18,6 +18,7 @@ import { } from '../constants/AppConstants'; import CaseListSearch from './CaseListSearch'; import CaseListTable from './CaseListTable'; +import CaseListLoadMore from './CaseListLoadMore'; import OtherReviewsTable from './OtherReviewsTable'; import { fullWidth } from './constants'; @@ -105,7 +106,7 @@ class CaseListView extends React.PureComponent {

{COPY.CASE_LIST_TABLE_TITLE}

- +

{COPY.OTHER_REVIEWS_TABLE_TITLE}

From 4378eadea113527a59994bea57b06155cad0e4ea Mon Sep 17 00:00:00 2001 From: 631583 Date: Tue, 24 Oct 2023 08:10:31 -0700 Subject: [PATCH 04/20] remove alternate location vba_317a from RO17 --- client/constants/REGIONAL_OFFICE_FACILITY_ADDRESS.json | 9 +++++++++ client/constants/REGIONAL_OFFICE_INFORMATION.json | 2 +- .../hearing_admin_action_verify_address_task_spec.rb | 6 +++--- 3 files changed, 13 insertions(+), 4 deletions(-) diff --git a/client/constants/REGIONAL_OFFICE_FACILITY_ADDRESS.json b/client/constants/REGIONAL_OFFICE_FACILITY_ADDRESS.json index 95c468b2aed..558448003fa 100644 --- a/client/constants/REGIONAL_OFFICE_FACILITY_ADDRESS.json +++ b/client/constants/REGIONAL_OFFICE_FACILITY_ADDRESS.json @@ -721,6 +721,15 @@ "zip" : "39531", "timezone" : "America/Chicago" }, + "vc_0742V" :{ + "address_1" : "1118 Burlington Street", + "address_2" : null, + "address_3" : null, + "city" : "Holdrege", + "state" : "NE", + "zip" : "68949-1705", + "timezone" : "America/New_York" + }, "vha_402GA" : { "address_1" : "163 Van Buren Road", "address_2" : null, diff --git a/client/constants/REGIONAL_OFFICE_INFORMATION.json b/client/constants/REGIONAL_OFFICE_INFORMATION.json index df1489c956a..c2cf28a682d 100644 --- a/client/constants/REGIONAL_OFFICE_INFORMATION.json +++ b/client/constants/REGIONAL_OFFICE_INFORMATION.json @@ -157,7 +157,7 @@ "timezone": "America/New_York", "hold_hearings": true, "facility_locator_id": "vba_317", - "alternate_locations": ["vba_317a", "vc_0742V"] + "alternate_locations": ["vc_0742V"] }, "RO18": { "label": "Winston-Salem regional office", diff --git a/spec/models/tasks/hearing_admin_action_verify_address_task_spec.rb b/spec/models/tasks/hearing_admin_action_verify_address_task_spec.rb index e8f31318ea2..70ccabcad90 100644 --- a/spec/models/tasks/hearing_admin_action_verify_address_task_spec.rb +++ b/spec/models/tasks/hearing_admin_action_verify_address_task_spec.rb @@ -54,9 +54,9 @@ ahls = appeal.class.first.available_hearing_locations.map(&:facility_id).uniq - # St. Petersburg RO facility id, and 2 alternate facilities - expect(ahls.count).to eq 3 - expect(ahls).to match_array(%w[vba_317 vba_317a vc_0742V]) + # St. Petersburg RO facility id, and 1 alternate facility + expect(ahls.count).to eq 2 + expect(ahls).to match_array(%w[vba_317 vc_0742V]) end it "throws an access error trying to update from params with random user" do From 02c50b4b3fa52da3ef4f0ec4bf2c6fa6fc2800d9 Mon Sep 17 00:00:00 2001 From: AimanK Date: Wed, 22 Nov 2023 14:20:57 -0500 Subject: [PATCH 05/20] Initial commit to test standard local behavior --- app/services/appeal_finder.rb | 20 +++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-) diff --git a/app/services/appeal_finder.rb b/app/services/appeal_finder.rb index ca0be428d50..b90f91201cc 100644 --- a/app/services/appeal_finder.rb +++ b/app/services/appeal_finder.rb @@ -2,21 +2,23 @@ class AppealFinder class << self - def find_appeals_with_file_numbers(file_numbers, last_id = 0) + def find_appeals_with_file_numbers(file_numbers) return [] if file_numbers.empty? MetricsService.record("VACOLS: Get appeal information for file_numbers #{file_numbers}", service: :queue, name: "VeteranFinderQuery.find_appeals_with_file_numbers") do - # limit set to 11 so we can determine if there is more to load + appeals = Appeal.established.where(veteran_file_number: file_numbers).to_a +=begin appeals = Appeal.established - .where(veteran_file_number: file_numbers).where(Appeal.arel_table[:id].gt(last_id)) - .includes(:decision_issues, :nod_date_updates, - :appellant_substitution, :hearings, - :request_issues, :work_mode, - :tasks, :available_hearing_locations, - :docket_switch, :remand_supplemental_claims) - .order(:id).limit(11).to_a + .includes(:cached_appeal_attributes) + .where(veteran_file_number: file_numbers, user_id: user.user_id) + .select(:docket_type, :stream_docket_number, :appellant_first_name, + :appellant_middle_initial, :appellant_last_name, :status, + :stream_type, :issue_count, :decision_date) + + .to_a +=end begin appeals.concat(LegacyAppeal.fetch_appeals_by_file_number(*file_numbers)) rescue ActiveRecord::RecordNotFound From d562b18fe67cfcf847c791696d7ac21e4e313417 Mon Sep 17 00:00:00 2001 From: AimanK Date: Tue, 28 Nov 2023 09:39:30 -0500 Subject: [PATCH 06/20] Initial proposed solution commit --- app/controllers/appeals_controller.rb | 4 +- .../work_queue/appeal_serializer_search.rb | 70 +++++++++++++++++ app/services/appeal_finder.rb | 21 +++-- client/app/queue/utils.js | 76 +++++++++++++++++++ 4 files changed, 158 insertions(+), 13 deletions(-) create mode 100644 app/models/serializers/work_queue/appeal_serializer_search.rb diff --git a/app/controllers/appeals_controller.rb b/app/controllers/appeals_controller.rb index a2f752a284c..3106ecfa300 100644 --- a/app/controllers/appeals_controller.rb +++ b/app/controllers/appeals_controller.rb @@ -27,7 +27,7 @@ def index ).call else CaseSearchResultsForVeteranFileNumber.new( - file_number_or_ssn: case_search, user: current_user, last_id: params[:last_id] + file_number_or_ssn: case_search, user: current_user ).call end @@ -214,7 +214,7 @@ def set_application def json_appeals(appeal) if appeal.is_a?(Appeal) - WorkQueue::AppealSerializer.new(appeal, params: { user: current_user }).serializable_hash + WorkQueue::AppealSerializerSearch.new(appeal, params: { user: current_user }).serializable_hash else WorkQueue::LegacyAppealSerializer.new(appeal, params: { user: current_user }).serializable_hash end diff --git a/app/models/serializers/work_queue/appeal_serializer_search.rb b/app/models/serializers/work_queue/appeal_serializer_search.rb new file mode 100644 index 00000000000..c83f0bd41e2 --- /dev/null +++ b/app/models/serializers/work_queue/appeal_serializer_search.rb @@ -0,0 +1,70 @@ +# frozen_string_literal: true + +class WorkQueue::AppealSerializerSearch + include FastJsonapi::ObjectSerializer + extend Helpers::AppealHearingHelper + + attribute :assigned_attorney + attribute :assigned_judge + + attribute :current_user_timezone do |_, params| + params[:user]&.timezone + end + + attribute :contested_claim, &:contested_claim? + + attribute :issues do |object| + object.request_issues.active_or_decided_or_withdrawn.includes(:remand_reasons).map do |issue| + { + id: issue.id, + program: issue.benefit_type, + description: issue.description, + notes: issue.notes, + diagnostic_code: issue.contested_rating_issue_diagnostic_code, + remand_reasons: issue.remand_reasons, + closed_status: issue.closed_status, + decision_date: issue.decision_date + } + end + end + + attribute :status + + attribute :appellant_is_not_veteran + + attribute :appellant_full_name do |object| + object.claimant&.name + end + + attribute :appellant_first_name do |object| + object.claimant&.first_name + end + + attribute :appellant_middle_name do |object| + object.claimant&.middle_name + end + + attribute :appellant_last_name do |object| + object.claimant&.last_name + end + + attribute :veteran_death_date + + attribute :veteran_file_number + + attribute :veteran_full_name do |object| + object.veteran ? object.veteran.name.formatted(:readable_full) : "Cannot locate" + end + + attribute :type + attribute :vacate_type + attribute :aod, &:advanced_on_docket? + attribute :docket_name + attribute :docket_number + attribute :decision_date + attribute :withdrawal_date + + attribute :caseflow_veteran_id do |object| + object.veteran ? object.veteran.id : nil + end +end diff --git a/app/services/appeal_finder.rb b/app/services/appeal_finder.rb index b90f91201cc..30e586b0798 100644 --- a/app/services/appeal_finder.rb +++ b/app/services/appeal_finder.rb @@ -8,22 +8,21 @@ def find_appeals_with_file_numbers(file_numbers) MetricsService.record("VACOLS: Get appeal information for file_numbers #{file_numbers}", service: :queue, name: "VeteranFinderQuery.find_appeals_with_file_numbers") do - appeals = Appeal.established.where(veteran_file_number: file_numbers).to_a -=begin - appeals = Appeal.established - .includes(:cached_appeal_attributes) - .where(veteran_file_number: file_numbers, user_id: user.user_id) - .select(:docket_type, :stream_docket_number, :appellant_first_name, - :appellant_middle_initial, :appellant_last_name, :status, - :stream_type, :issue_count, :decision_date) - + ## appeals = Appeal.established.where(veteran_file_number: file_numbers).to_a + ama_appeals = Appeal.established + .includes(:docket_switch, :available_hearing_locations, :tasks, :work_mode, + :request_issues, :hearings, :appellant_substitution, :nod_date_updates, + :decision_issues) + .where(veteran_file_number: file_numbers) .to_a -=end begin - appeals.concat(LegacyAppeal.fetch_appeals_by_file_number(*file_numbers)) + legacy_appeals = LegacyAppeal.fetch_appeals_by_file_number(*file_numbers) rescue ActiveRecord::RecordNotFound # file number could not be found. don't raise exception and not return, just ignore. + legacy_appeals = [] end + appeals = ama_appeals + legacy_appeals + appeals end end diff --git a/client/app/queue/utils.js b/client/app/queue/utils.js index 57d8b466561..fdb00879f2f 100644 --- a/client/app/queue/utils.js +++ b/client/app/queue/utils.js @@ -398,6 +398,8 @@ const prepareLocationHistoryForStore = (appeal) => { return locationHistory; }; + +/** export const prepareAppealForStore = (appeals) => { const appealHash = appeals.reduce((accumulator, appeal) => { const { @@ -523,6 +525,80 @@ export const prepareAppealForStore = (appeals) => { }; }; +**/ + + + + +export const prepareAppealForStore = (appeals) => { + const appealHash = appeals.reduce((accumulator, appeal) => { + const { + attributes: { issues }, + } = appeal; + + accumulator[appeal.attributes.external_id] = { + id: appeal.id, + externalId: appeal.attributes.external_id, + docketName: appeal.attributes.docket_name, + withdrawn: appeal.attributes.withdrawn, + removed: appeal.attributes.removed, + overtime: appeal.attributes.overtime, + contestedClaim: appeal.attributes.contested_claim, + veteranAppellantDeceased: appeal.attributes.veteran_appellant_deceased, + withdrawalDate: formatDateStrUtc(appeal.attributes.withdrawal_date), + isLegacyAppeal: appeal.attributes.docket_name === 'legacy', + caseType: appeal.attributes.type, + isAdvancedOnDocket: appeal.attributes.aod, + issueCount: (appeal.attributes.docket_name === 'legacy' ? + getUndecidedIssues(issues) : + issues + ).length, + docketNumber: appeal.attributes.docket_number, + assignedAttorney: appeal.attributes.assigned_attorney, + assignedJudge: appeal.attributes.assigned_judge, + distributedToJudge: appeal.attributes.distributed_to_a_judge, + veteranFullName: appeal.attributes.veteran_full_name, + veteranFileNumber: appeal.attributes.veteran_file_number, + vacateType: appeal.attributes.vacate_type, + }; + + return accumulator; + }, {}); + + const appealDetailsHash = appeals.reduce((accumulator, appeal) => { + accumulator[appeal.attributes.external_id] = { + hearings: prepareAppealHearingsForStore(appeal), + currentUserTimezone: appeal.attributes.current_user_timezone, + issues: prepareAppealIssuesForStore(appeal), + appellantIsNotVeteran: appeal.attributes.appellant_is_not_veteran, + appellantFullName: appeal.attributes.appellant_full_name, + contestedClaim: appeal.attributes.contested_claim, + assignedToLocation: appeal.attributes.assigned_to_location, + veteranDateOfDeath: appeal.attributes.veteran_death_date, + veteranParticipantId: appeal.attributes.veteran_participant_id, + closestRegionalOffice: appeal.attributes.closest_regional_office, + closestRegionalOfficeLabel: + appeal.attributes.closest_regional_office_label, + externalId: appeal.attributes.external_id, + efolderLink: appeal.attributes.efolder_link, + status: appeal.attributes.status, + decisionDate: appeal.attributes.decision_date, + caseflowVeteranId: appeal.attributes.caseflow_veteran_id, + locationHistory: prepareLocationHistoryForStore(appeal), + }; + + return accumulator; + }, {}); + + return { + appeals: appealHash, + appealDetails: appealDetailsHash, + }; +}; + + + + export const prepareClaimReviewForStore = (claimReviews) => { const claimReviewHash = claimReviews.reduce((accumulator, claimReview) => { const key = `${claimReview.review_type}-${claimReview.claim_id}`; From 2452111e3d91caf2b3fd2283488a1126de66282b Mon Sep 17 00:00:00 2001 From: AimanK Date: Tue, 28 Nov 2023 12:46:49 -0500 Subject: [PATCH 07/20] Cleaning up prepareAppealForStore appeals hashes --- app/controllers/appeals_controller.rb | 2 +- .../work_queue/appeal_serializer_search.rb | 12 ++++++++++++ client/app/queue/utils.js | 10 ---------- 3 files changed, 13 insertions(+), 11 deletions(-) diff --git a/app/controllers/appeals_controller.rb b/app/controllers/appeals_controller.rb index 3106ecfa300..da9b692039a 100644 --- a/app/controllers/appeals_controller.rb +++ b/app/controllers/appeals_controller.rb @@ -214,7 +214,7 @@ def set_application def json_appeals(appeal) if appeal.is_a?(Appeal) - WorkQueue::AppealSerializerSearch.new(appeal, params: { user: current_user }).serializable_hash + WorkQueue::AppealSerializer.new(appeal, params: { user: current_user }).serializable_hash else WorkQueue::LegacyAppealSerializer.new(appeal, params: { user: current_user }).serializable_hash end diff --git a/app/models/serializers/work_queue/appeal_serializer_search.rb b/app/models/serializers/work_queue/appeal_serializer_search.rb index c83f0bd41e2..740a5ee256c 100644 --- a/app/models/serializers/work_queue/appeal_serializer_search.rb +++ b/app/models/serializers/work_queue/appeal_serializer_search.rb @@ -30,6 +30,18 @@ class WorkQueue::AppealSerializerSearch attribute :status + attribute(:hearings) do |object, params| + # For substitution appeals after death dismissal, we need to show hearings from the source appeal + # in addition to those on the new/target appeal; this avoids copying them to new appeal stream + associated_hearings = [] + + if object.separate_appeal_substitution? + associated_hearings = hearings(object.appellant_substitution.source_appeal, params) + end + + associated_hearings + hearings(object, params) + end + attribute :appellant_is_not_veteran attribute :appellant_full_name do |object| diff --git a/client/app/queue/utils.js b/client/app/queue/utils.js index fdb00879f2f..7168a7f7c76 100644 --- a/client/app/queue/utils.js +++ b/client/app/queue/utils.js @@ -541,14 +541,12 @@ export const prepareAppealForStore = (appeals) => { externalId: appeal.attributes.external_id, docketName: appeal.attributes.docket_name, withdrawn: appeal.attributes.withdrawn, - removed: appeal.attributes.removed, overtime: appeal.attributes.overtime, contestedClaim: appeal.attributes.contested_claim, veteranAppellantDeceased: appeal.attributes.veteran_appellant_deceased, withdrawalDate: formatDateStrUtc(appeal.attributes.withdrawal_date), isLegacyAppeal: appeal.attributes.docket_name === 'legacy', caseType: appeal.attributes.type, - isAdvancedOnDocket: appeal.attributes.aod, issueCount: (appeal.attributes.docket_name === 'legacy' ? getUndecidedIssues(issues) : issues @@ -568,19 +566,11 @@ export const prepareAppealForStore = (appeals) => { const appealDetailsHash = appeals.reduce((accumulator, appeal) => { accumulator[appeal.attributes.external_id] = { hearings: prepareAppealHearingsForStore(appeal), - currentUserTimezone: appeal.attributes.current_user_timezone, - issues: prepareAppealIssuesForStore(appeal), - appellantIsNotVeteran: appeal.attributes.appellant_is_not_veteran, appellantFullName: appeal.attributes.appellant_full_name, contestedClaim: appeal.attributes.contested_claim, assignedToLocation: appeal.attributes.assigned_to_location, - veteranDateOfDeath: appeal.attributes.veteran_death_date, veteranParticipantId: appeal.attributes.veteran_participant_id, - closestRegionalOffice: appeal.attributes.closest_regional_office, - closestRegionalOfficeLabel: - appeal.attributes.closest_regional_office_label, externalId: appeal.attributes.external_id, - efolderLink: appeal.attributes.efolder_link, status: appeal.attributes.status, decisionDate: appeal.attributes.decision_date, caseflowVeteranId: appeal.attributes.caseflow_veteran_id, From dc94ad97fac46796e688d0e350146d0b3fa04d17 Mon Sep 17 00:00:00 2001 From: AimanK Date: Tue, 5 Dec 2023 09:53:19 -0500 Subject: [PATCH 08/20] AMA Appeal search serializer improvements --- .../work_queue/appeal_serializer_search.rb | 24 +++++++++---------- app/workflows/case_search_results_base.rb | 2 +- client/app/queue/utils.js | 13 +++------- 3 files changed, 16 insertions(+), 23 deletions(-) diff --git a/app/models/serializers/work_queue/appeal_serializer_search.rb b/app/models/serializers/work_queue/appeal_serializer_search.rb index 740a5ee256c..60fc3d6ec1e 100644 --- a/app/models/serializers/work_queue/appeal_serializer_search.rb +++ b/app/models/serializers/work_queue/appeal_serializer_search.rb @@ -4,9 +4,15 @@ class WorkQueue::AppealSerializerSearch include FastJsonapi::ObjectSerializer extend Helpers::AppealHearingHelper + set_type :appeal + attribute :assigned_attorney attribute :assigned_judge + attribute :current_user_email do |_, params| + params[:user]&.email + end + attribute :current_user_timezone do |_, params| params[:user]&.timezone end @@ -42,24 +48,14 @@ class WorkQueue::AppealSerializerSearch associated_hearings + hearings(object, params) end + attribute :assigned_to_location + attribute :appellant_is_not_veteran attribute :appellant_full_name do |object| object.claimant&.name end - attribute :appellant_first_name do |object| - object.claimant&.first_name - end - - attribute :appellant_middle_name do |object| - object.claimant&.middle_name - end - - attribute :appellant_last_name do |object| - object.claimant&.last_name - end - attribute :veteran_death_date attribute :veteran_file_number @@ -68,12 +64,16 @@ class WorkQueue::AppealSerializerSearch object.veteran ? object.veteran.name.formatted(:readable_full) : "Cannot locate" end + attribute :external_id, &:uuid + attribute :type attribute :vacate_type attribute :aod, &:advanced_on_docket? attribute :docket_name attribute :docket_number + attribute :docket_range_date attribute :decision_date + attribute :nod_date, &:receipt_date attribute :withdrawal_date attribute :caseflow_veteran_id do |object| diff --git a/app/workflows/case_search_results_base.rb b/app/workflows/case_search_results_base.rb index 46f05c018ee..5f1922d0f53 100644 --- a/app/workflows/case_search_results_base.rb +++ b/app/workflows/case_search_results_base.rb @@ -60,7 +60,7 @@ def veterans_user_can_access def json_appeals(appeals) ama_appeals, legacy_appeals = appeals.partition { |appeal| appeal.is_a?(Appeal) } - ama_hash = WorkQueue::AppealSerializer.new( + ama_hash = WorkQueue::AppealSerializerSearch.new( ama_appeals, is_collection: true, params: { user: user } ).serializable_hash diff --git a/client/app/queue/utils.js b/client/app/queue/utils.js index 7168a7f7c76..22060dcaa8b 100644 --- a/client/app/queue/utils.js +++ b/client/app/queue/utils.js @@ -399,7 +399,6 @@ const prepareLocationHistoryForStore = (appeal) => { }; -/** export const prepareAppealForStore = (appeals) => { const appealHash = appeals.reduce((accumulator, appeal) => { const { @@ -525,12 +524,7 @@ export const prepareAppealForStore = (appeals) => { }; }; -**/ - - - - -export const prepareAppealForStore = (appeals) => { +export const prepareAppealForSearchStore = (appeals) => { const appealHash = appeals.reduce((accumulator, appeal) => { const { attributes: { issues }, @@ -567,6 +561,8 @@ export const prepareAppealForStore = (appeals) => { accumulator[appeal.attributes.external_id] = { hearings: prepareAppealHearingsForStore(appeal), appellantFullName: appeal.attributes.appellant_full_name, + currentUserEmail: appeal.attributes.current_user_email, + currentUserTimezone: appeal.attributes.current_user_timezone, contestedClaim: appeal.attributes.contested_claim, assignedToLocation: appeal.attributes.assigned_to_location, veteranParticipantId: appeal.attributes.veteran_participant_id, @@ -586,9 +582,6 @@ export const prepareAppealForStore = (appeals) => { }; }; - - - export const prepareClaimReviewForStore = (claimReviews) => { const claimReviewHash = claimReviews.reduce((accumulator, claimReview) => { const key = `${claimReview.review_type}-${claimReview.claim_id}`; From 1ab2c8413b72ef1dc2d2c9d8687241fa2b6372ad Mon Sep 17 00:00:00 2001 From: AimanK Date: Wed, 6 Dec 2023 08:36:28 -0500 Subject: [PATCH 09/20] Change serializer to accommodate different appeals --- .../work_queue/appeal_serializer_search.rb | 52 +++++++++++++++++++ client/app/queue/CaseList/CaseListActions.js | 4 +- client/app/queue/utils.js | 1 + 3 files changed, 55 insertions(+), 2 deletions(-) diff --git a/app/models/serializers/work_queue/appeal_serializer_search.rb b/app/models/serializers/work_queue/appeal_serializer_search.rb index 60fc3d6ec1e..381e05c9ab1 100644 --- a/app/models/serializers/work_queue/appeal_serializer_search.rb +++ b/app/models/serializers/work_queue/appeal_serializer_search.rb @@ -9,6 +9,17 @@ class WorkQueue::AppealSerializerSearch attribute :assigned_attorney attribute :assigned_judge + attribute :appellant_hearing_email_recipient do |object| + object.email_recipients.find_by(type: "AppellantHearingEmailRecipient") + end + attribute :representative_hearing_email_recipient do |object| + object.email_recipients.find_by(type: "RepresentativeHearingEmailRecipient") + end + + attribute :appellant_email_address do |object| + object.appellant ? object.appellant.email_address : "Cannot Find Appellant" + end + attribute :current_user_email do |_, params| params[:user]&.email end @@ -48,14 +59,41 @@ class WorkQueue::AppealSerializerSearch associated_hearings + hearings(object, params) end + attribute :withdrawn, &:withdrawn? + + attribute :removed, &:removed? + + attribute :overtime, &:overtime? + + attribute :veteran_appellant_deceased, &:veteran_appellant_deceased? + attribute :assigned_to_location + attribute :distributed_to_a_judge, &:distributed_to_a_judge? + attribute :appellant_is_not_veteran attribute :appellant_full_name do |object| object.claimant&.name end + attribute :appellant_relationship, &:appellant_relationship + + attribute :has_poa do |appeal| + appeal.claimant&.power_of_attorney + end + + attribute :cavc_remand do |object| + if object.cavc_remand + WorkQueue::CavcRemandSerializer.new(object.cavc_remand).serializable_hash[:data][:attributes] + end + end + + attribute :show_post_cavc_stream_msg do |object| + cavc_remand = CavcRemand.find_by(source_appeal_id: object.id) + cavc_remand.present? && cavc_remand.cavc_remands_appellant_substitution.present? + end + attribute :veteran_death_date attribute :veteran_file_number @@ -79,4 +117,18 @@ class WorkQueue::AppealSerializerSearch attribute :caseflow_veteran_id do |object| object.veteran ? object.veteran.id : nil end + + attribute :document_id do |object| + object.latest_attorney_case_review&.document_id + end + + attribute :attorney_case_review_id do |object| + object.latest_attorney_case_review&.id + end + + attribute :docket_switch do |object| + if object.docket_switch + WorkQueue::DocketSwitchSerializer.new(object.docket_switch).serializable_hash[:data][:attributes] + end + end end diff --git a/client/app/queue/CaseList/CaseListActions.js b/client/app/queue/CaseList/CaseListActions.js index b9d7b8d82ec..8a9264b3edc 100644 --- a/client/app/queue/CaseList/CaseListActions.js +++ b/client/app/queue/CaseList/CaseListActions.js @@ -4,7 +4,7 @@ import * as Constants from './actionTypes'; import { get, size } from 'lodash'; import { onReceiveAppealDetails, onReceiveClaimReviewDetails } from '../QueueActions'; -import { prepareAppealForStore, prepareClaimReviewForStore } from '../utils'; +import { prepareAppealForStore, prepareAppealForSearchStore, prepareClaimReviewForStore } from '../utils'; import ValidatorsUtil from '../../util/ValidatorsUtil'; const { validSSN, validFileNum, validDocketNum } = ValidatorsUtil; @@ -54,7 +54,7 @@ export const fetchedNoAppeals = (searchQuery) => ({ }); export const onReceiveAppeals = (appeals) => (dispatch) => { - dispatch(onReceiveAppealDetails(prepareAppealForStore(appeals))); + dispatch(onReceiveAppealDetails(prepareAppealForSearchStore(appeals))); dispatch({ type: Constants.RECEIVED_APPEALS_USING_VETERAN_ID_SUCCESS }); diff --git a/client/app/queue/utils.js b/client/app/queue/utils.js index 6cdd1643362..bb1e6868921 100644 --- a/client/app/queue/utils.js +++ b/client/app/queue/utils.js @@ -541,6 +541,7 @@ export const prepareAppealForSearchStore = (appeals) => { withdrawalDate: formatDateStrUtc(appeal.attributes.withdrawal_date), isLegacyAppeal: appeal.attributes.docket_name === 'legacy', caseType: appeal.attributes.type, + isAdvancedOnDocket: appeal.attributes.aod, issueCount: (appeal.attributes.docket_name === 'legacy' ? getUndecidedIssues(issues) : issues From 642c86dac23c14eb902cab9d790900e982551905 Mon Sep 17 00:00:00 2001 From: AimanK Date: Thu, 7 Dec 2023 09:57:37 -0500 Subject: [PATCH 10/20] Make fixes to legacy serializer/remove LoadMore --- .../legacy_appeal_search_serializer.rb | 100 ++++++++++++++++++ app/workflows/case_search_results_base.rb | 2 +- client/COPY.json | 1 - client/app/queue/CaseListLoadMore.jsx | 35 ------ client/app/queue/CaseListView.jsx | 2 - 5 files changed, 101 insertions(+), 39 deletions(-) create mode 100644 app/models/serializers/work_queue/legacy_appeal_search_serializer.rb delete mode 100644 client/app/queue/CaseListLoadMore.jsx diff --git a/app/models/serializers/work_queue/legacy_appeal_search_serializer.rb b/app/models/serializers/work_queue/legacy_appeal_search_serializer.rb new file mode 100644 index 00000000000..7cd374f20e6 --- /dev/null +++ b/app/models/serializers/work_queue/legacy_appeal_search_serializer.rb @@ -0,0 +1,100 @@ +# frozen_string_literal: true + +class WorkQueue::LegacyAppealSearchSerializer + include FastJsonapi::ObjectSerializer + extend Helpers::AppealHearingHelper + + set_type :legacy_appeal + + attribute :assigned_attorney + attribute :assigned_judge + + attribute :issues do |object| + object.issues.map do |issue| + WorkQueue::LegacyIssueSerializer.new(issue).serializable_hash[:data][:attributes] + end + end + + attribute :hearings do |object, params| + hearings(object, params) + end + + attribute :completed_hearing_on_previous_appeal? + + attribute :appellant_is_not_veteran, &:appellant_is_not_veteran + + attribute :appellant_full_name, &:appellant_name + + attribute :appellant_address, &:appellant_address + + attribute :appellant_tz, &:appellant_tz + + attribute :appellant_relationship + attribute :assigned_to_location + attribute :vbms_id, &:sanitized_vbms_id + attribute :veteran_full_name + attribute :veteran_death_date + attribute :veteran_appellant_deceased, &:veteran_appellant_deceased? + # Aliasing the vbms_id to make it clear what we're returning. + attribute :veteran_file_number, &:sanitized_vbms_id + attribute :veteran_participant_id do |object| + object&.veteran&.participant_id + end + attribute :efolder_link do + ENV["CLAIM_EVIDENCE_EFOLDER_BASE_URL"] + end + attribute :external_id, &:vacols_id + attribute :type + attribute :aod + attribute :docket_number + attribute :docket_range_date, &:docket_date + attribute :status + attribute :decision_date + attribute :form9_date + attribute :nod_date + attribute :certification_date + attribute :paper_case, &:paper_case? + attribute :overtime, &:overtime? + attribute :caseflow_veteran_id do |object| + object.veteran ? object.veteran.id : nil + end + + attribute(:available_hearing_locations) { |object| available_hearing_locations(object) } + + attribute :docket_name do + "legacy" + end + + attribute :document_id do |object| + latest_vacols_attorney_case_review(object)&.document_id + end + + attribute :can_edit_document_id do |object, params| + LegacyDocumentIdPolicy.new( + user: params[:user], + case_review: latest_vacols_attorney_case_review(object) + ).editable? + end + + attribute :attorney_case_review_id do |object| + latest_vacols_attorney_case_review(object)&.vacols_id + end + + attribute :current_user_email do |_, params| + params[:user]&.email + end + + attribute :current_user_timezone do |_, params| + params[:user]&.timezone + end + + attribute :location_history do |object| + object.location_history.map do |location| + WorkQueue::PriorlocSerializer.new(location).serializable_hash[:data][:attributes] + end + end + + def self.latest_vacols_attorney_case_review(object) + VACOLS::CaseAssignment.latest_task_for_appeal(object.vacols_id) + end +end diff --git a/app/workflows/case_search_results_base.rb b/app/workflows/case_search_results_base.rb index 5f1922d0f53..ded5e50226b 100644 --- a/app/workflows/case_search_results_base.rb +++ b/app/workflows/case_search_results_base.rb @@ -64,7 +64,7 @@ def json_appeals(appeals) ama_appeals, is_collection: true, params: { user: user } ).serializable_hash - legacy_hash = WorkQueue::LegacyAppealSerializer.new( + legacy_hash = WorkQueue::LegacyAppealSearchSerializer.new( legacy_appeals, is_collection: true, params: { user: user } ).serializable_hash diff --git a/client/COPY.json b/client/COPY.json index 80fe6848421..72eae2ee16f 100644 --- a/client/COPY.json +++ b/client/COPY.json @@ -1,7 +1,6 @@ { "CASE_SEARCH_HOME_PAGE_HEADING": "Veteran Case Search", "CASE_SEARCH_INPUT_PLACEHOLDER": "Enter a file number, SSN, or AMA docket number", - "CASE_SEARCH_LOAD_MORE_TEXT": "Load More Cases", "CASE_SEARCH_INPUT_INSTRUCTION": "Please enter a valid claims file number, SSN, or AMA docket number (with hyphen) to search for all available cases.", "CASE_SEARCH_ERROR_EMPTY_SEARCH_TERM": "Cannot search for no text", "CASE_SEARCH_ERROR_INVALID_ID_HEADING": "Invalid search parameter ā€œ%sā€", diff --git a/client/app/queue/CaseListLoadMore.jsx b/client/app/queue/CaseListLoadMore.jsx deleted file mode 100644 index 46d8743b6e1..00000000000 --- a/client/app/queue/CaseListLoadMore.jsx +++ /dev/null @@ -1,35 +0,0 @@ -import React from 'react'; -import { connect } from 'react-redux'; -import { withRouter } from 'react-router-dom'; -import { bindActionCreators } from 'redux'; -import PropTypes from 'prop-types'; -import COPY from '../../COPY'; - -class CaseListLoadMore extends React.PureComponent { - render() { - return ( - - { COPY.CASE_SEARCH_LOAD_MORE_TEXT } - - ); - } -} - -CaseListLoadMore.propTypes = { - caseListCount: PropTypes.number -}; - -CaseListLoadMore.defaultProps = { - caseListCount: 0 -}; - -const mapDispatchToProps = (dispatch) => bindActionCreators({}, dispatch); - -const mapStateToProps = (state) => ({ caseList: state.caseList }); - -export default withRouter( - connect( - mapStateToProps, - mapDispatchToProps - )(CaseListLoadMore) -); diff --git a/client/app/queue/CaseListView.jsx b/client/app/queue/CaseListView.jsx index 85d596b98f2..0f951cdbdc2 100644 --- a/client/app/queue/CaseListView.jsx +++ b/client/app/queue/CaseListView.jsx @@ -18,7 +18,6 @@ import { } from '../constants/AppConstants'; import CaseListSearch from './CaseListSearch'; import CaseListTable from './CaseListTable'; -import CaseListLoadMore from './CaseListLoadMore'; import OtherReviewsTable from './OtherReviewsTable'; import { fullWidth } from './constants'; @@ -106,7 +105,6 @@ class CaseListView extends React.PureComponent {

{COPY.CASE_LIST_TABLE_TITLE}

-

{COPY.OTHER_REVIEWS_TABLE_TITLE}

From c4ac5977bd1329b125a95331ef162018d84285e3 Mon Sep 17 00:00:00 2001 From: AimanK Date: Thu, 7 Dec 2023 09:58:03 -0500 Subject: [PATCH 11/20] Add fixes to AMA appeal serializer --- .../serializers/work_queue/appeal_serializer_search.rb | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/app/models/serializers/work_queue/appeal_serializer_search.rb b/app/models/serializers/work_queue/appeal_serializer_search.rb index 381e05c9ab1..05bf5cb5374 100644 --- a/app/models/serializers/work_queue/appeal_serializer_search.rb +++ b/app/models/serializers/work_queue/appeal_serializer_search.rb @@ -77,6 +77,12 @@ class WorkQueue::AppealSerializerSearch object.claimant&.name end + attribute :appellant_address do |object| + object.claimant&.address + end + + attribute :appellant_tz, &:appellant_tz + attribute :appellant_relationship, &:appellant_relationship attribute :has_poa do |appeal| From cfe99d292942e31908043e988ad31b09c389319a Mon Sep 17 00:00:00 2001 From: 631583 Date: Mon, 11 Dec 2023 10:53:30 -0800 Subject: [PATCH 12/20] check attorney judge and hearing coordinator in appeal serializer --- app/models/serializers/work_queue/appeal_serializer.rb | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/app/models/serializers/work_queue/appeal_serializer.rb b/app/models/serializers/work_queue/appeal_serializer.rb index bfa23c51fe4..4bbd4cf6f0b 100644 --- a/app/models/serializers/work_queue/appeal_serializer.rb +++ b/app/models/serializers/work_queue/appeal_serializer.rb @@ -103,7 +103,15 @@ class WorkQueue::AppealSerializer attribute :veteran_appellant_deceased, &:veteran_appellant_deceased? - attribute :assigned_to_location + attribute :assigned_to_location do |object, params| + if object&.distributed_to_a_judge? + if (params[:user]&.judge? || params[:user]&.attorney? || User.list_hearing_coordinators.include?(params[:user])) + object.assigned_to_location + end + else + object.assigned_to_location + end + end attribute :distributed_to_a_judge, &:distributed_to_a_judge? From e17042fbece098cb541a39357f46a7293c03ca51 Mon Sep 17 00:00:00 2001 From: raymond-hughes Date: Mon, 11 Dec 2023 20:34:04 -0500 Subject: [PATCH 13/20] Refactor serializer --- ..._search.rb => appeal_search_serializer.rb} | 57 +------------------ app/workflows/case_search_results_base.rb | 2 +- db/schema.rb | 5 +- 3 files changed, 5 insertions(+), 59 deletions(-) rename app/models/serializers/work_queue/{appeal_serializer_search.rb => appeal_search_serializer.rb} (59%) diff --git a/app/models/serializers/work_queue/appeal_serializer_search.rb b/app/models/serializers/work_queue/appeal_search_serializer.rb similarity index 59% rename from app/models/serializers/work_queue/appeal_serializer_search.rb rename to app/models/serializers/work_queue/appeal_search_serializer.rb index 05bf5cb5374..d72ff4547a8 100644 --- a/app/models/serializers/work_queue/appeal_serializer_search.rb +++ b/app/models/serializers/work_queue/appeal_search_serializer.rb @@ -1,33 +1,11 @@ # frozen_string_literal: true -class WorkQueue::AppealSerializerSearch +class WorkQueue::AppealSearchSerializer include FastJsonapi::ObjectSerializer extend Helpers::AppealHearingHelper set_type :appeal - attribute :assigned_attorney - attribute :assigned_judge - - attribute :appellant_hearing_email_recipient do |object| - object.email_recipients.find_by(type: "AppellantHearingEmailRecipient") - end - attribute :representative_hearing_email_recipient do |object| - object.email_recipients.find_by(type: "RepresentativeHearingEmailRecipient") - end - - attribute :appellant_email_address do |object| - object.appellant ? object.appellant.email_address : "Cannot Find Appellant" - end - - attribute :current_user_email do |_, params| - params[:user]&.email - end - - attribute :current_user_timezone do |_, params| - params[:user]&.timezone - end - attribute :contested_claim, &:contested_claim? attribute :issues do |object| @@ -71,35 +49,10 @@ class WorkQueue::AppealSerializerSearch attribute :distributed_to_a_judge, &:distributed_to_a_judge? - attribute :appellant_is_not_veteran - attribute :appellant_full_name do |object| object.claimant&.name end - attribute :appellant_address do |object| - object.claimant&.address - end - - attribute :appellant_tz, &:appellant_tz - - attribute :appellant_relationship, &:appellant_relationship - - attribute :has_poa do |appeal| - appeal.claimant&.power_of_attorney - end - - attribute :cavc_remand do |object| - if object.cavc_remand - WorkQueue::CavcRemandSerializer.new(object.cavc_remand).serializable_hash[:data][:attributes] - end - end - - attribute :show_post_cavc_stream_msg do |object| - cavc_remand = CavcRemand.find_by(source_appeal_id: object.id) - cavc_remand.present? && cavc_remand.cavc_remands_appellant_substitution.present? - end - attribute :veteran_death_date attribute :veteran_file_number @@ -124,14 +77,6 @@ class WorkQueue::AppealSerializerSearch object.veteran ? object.veteran.id : nil end - attribute :document_id do |object| - object.latest_attorney_case_review&.document_id - end - - attribute :attorney_case_review_id do |object| - object.latest_attorney_case_review&.id - end - attribute :docket_switch do |object| if object.docket_switch WorkQueue::DocketSwitchSerializer.new(object.docket_switch).serializable_hash[:data][:attributes] diff --git a/app/workflows/case_search_results_base.rb b/app/workflows/case_search_results_base.rb index ded5e50226b..81e4f3a224d 100644 --- a/app/workflows/case_search_results_base.rb +++ b/app/workflows/case_search_results_base.rb @@ -60,7 +60,7 @@ def veterans_user_can_access def json_appeals(appeals) ama_appeals, legacy_appeals = appeals.partition { |appeal| appeal.is_a?(Appeal) } - ama_hash = WorkQueue::AppealSerializerSearch.new( + ama_hash = WorkQueue::AppealSearchSerializer.new( ama_appeals, is_collection: true, params: { user: user } ).serializable_hash diff --git a/db/schema.rb b/db/schema.rb index 1de2cb0944b..338743203cb 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -1320,7 +1320,7 @@ t.string "appeals_type", null: false, comment: "Type of Appeal" t.datetime "created_at", comment: "Timestamp of when Noticiation was Created" t.boolean "email_enabled", default: true, null: false - t.string "email_notification_content", comment: "Full Email Text Content of Notification" + t.text "email_notification_content", comment: "Full Email Text Content of Notification" t.string "email_notification_external_id", comment: "VA Notify Notification Id for the email notification send through their API " t.string "email_notification_status", comment: "Status of the Email Notification" t.date "event_date", null: false, comment: "Date of Event" @@ -1331,7 +1331,7 @@ t.string "participant_id", comment: "ID of Participant" t.string "recipient_email", comment: "Participant's Email Address" t.string "recipient_phone_number", comment: "Participants Phone Number" - t.string "sms_notification_content", comment: "Full SMS Text Content of Notification" + t.text "sms_notification_content", comment: "Full SMS Text Content of Notification" t.string "sms_notification_external_id", comment: "VA Notify Notification Id for the sms notification send through their API " t.string "sms_notification_status", comment: "Status of SMS/Text Notification" t.datetime "updated_at", comment: "TImestamp of when Notification was Updated" @@ -1652,6 +1652,7 @@ t.boolean "national_cemetery_administration", default: false t.boolean "no_special_issues", default: false, comment: "Affirmative no special issues, added belatedly" t.boolean "nonrating_issue", default: false + t.boolean "pact_act", default: false, comment: "The Sergeant First Class (SFC) Heath Robinson Honoring our Promise to Address Comprehensive Toxics (PACT) Act" t.boolean "pension_united_states", default: false t.boolean "private_attorney_or_agent", default: false t.boolean "radiation", default: false From 9f830e30abd493cb4332f4274633bfa010d1e042 Mon Sep 17 00:00:00 2001 From: AimanK Date: Mon, 11 Dec 2023 21:29:05 -0500 Subject: [PATCH 14/20] Schema check in --- db/schema.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/db/schema.rb b/db/schema.rb index 1de2cb0944b..0f0b73041ba 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -10,7 +10,7 @@ # # It's strongly recommended that you check this file into your version control system. -ActiveRecord::Schema.define(version: 2023_10_16_132819) do +ActiveRecord::Schema.define(version: 2023_11_29_224254) do # These are extensions that must be enabled in order to support this database enable_extension "plpgsql" From 607bb98dcebd57ea0bf6ab43033007d793027296 Mon Sep 17 00:00:00 2001 From: AimanK Date: Tue, 12 Dec 2023 14:04:27 -0500 Subject: [PATCH 15/20] Schema Check in --- db/schema.rb | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/db/schema.rb b/db/schema.rb index 8d79f35c61a..0f0b73041ba 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -1320,7 +1320,7 @@ t.string "appeals_type", null: false, comment: "Type of Appeal" t.datetime "created_at", comment: "Timestamp of when Noticiation was Created" t.boolean "email_enabled", default: true, null: false - t.text "email_notification_content", comment: "Full Email Text Content of Notification" + t.string "email_notification_content", comment: "Full Email Text Content of Notification" t.string "email_notification_external_id", comment: "VA Notify Notification Id for the email notification send through their API " t.string "email_notification_status", comment: "Status of the Email Notification" t.date "event_date", null: false, comment: "Date of Event" @@ -1331,7 +1331,7 @@ t.string "participant_id", comment: "ID of Participant" t.string "recipient_email", comment: "Participant's Email Address" t.string "recipient_phone_number", comment: "Participants Phone Number" - t.text "sms_notification_content", comment: "Full SMS Text Content of Notification" + t.string "sms_notification_content", comment: "Full SMS Text Content of Notification" t.string "sms_notification_external_id", comment: "VA Notify Notification Id for the sms notification send through their API " t.string "sms_notification_status", comment: "Status of SMS/Text Notification" t.datetime "updated_at", comment: "TImestamp of when Notification was Updated" @@ -1652,7 +1652,6 @@ t.boolean "national_cemetery_administration", default: false t.boolean "no_special_issues", default: false, comment: "Affirmative no special issues, added belatedly" t.boolean "nonrating_issue", default: false - t.boolean "pact_act", default: false, comment: "The Sergeant First Class (SFC) Heath Robinson Honoring our Promise to Address Comprehensive Toxics (PACT) Act" t.boolean "pension_united_states", default: false t.boolean "private_attorney_or_agent", default: false t.boolean "radiation", default: false From 8b0e718e28669be6a53a82a1698767f61466918b Mon Sep 17 00:00:00 2001 From: AimanK Date: Wed, 13 Dec 2023 09:04:34 -0500 Subject: [PATCH 16/20] Revert serializer and restore master schema --- .../work_queue/appeal_search_serializer.rb | 55 +++++++++++++++++++ db/schema.rb | 2 +- 2 files changed, 56 insertions(+), 1 deletion(-) diff --git a/app/models/serializers/work_queue/appeal_search_serializer.rb b/app/models/serializers/work_queue/appeal_search_serializer.rb index d72ff4547a8..ba754828dd3 100644 --- a/app/models/serializers/work_queue/appeal_search_serializer.rb +++ b/app/models/serializers/work_queue/appeal_search_serializer.rb @@ -6,6 +6,28 @@ class WorkQueue::AppealSearchSerializer set_type :appeal + attribute :assigned_attorney + attribute :assigned_judge + + attribute :appellant_hearing_email_recipient do |object| + object.email_recipients.find_by(type: "AppellantHearingEmailRecipient") + end + attribute :representative_hearing_email_recipient do |object| + object.email_recipients.find_by(type: "RepresentativeHearingEmailRecipient") + end + + attribute :appellant_email_address do |object| + object.appellant ? object.appellant.email_address : "Cannot Find Appellant" + end + + attribute :current_user_email do |_, params| + params[:user]&.email + end + + attribute :current_user_timezone do |_, params| + params[:user]&.timezone + end + attribute :contested_claim, &:contested_claim? attribute :issues do |object| @@ -49,10 +71,35 @@ class WorkQueue::AppealSearchSerializer attribute :distributed_to_a_judge, &:distributed_to_a_judge? + attribute :appellant_is_not_veteran + attribute :appellant_full_name do |object| object.claimant&.name end + attribute :appellant_address do |object| + object.claimant&.address + end + + attribute :appellant_tz, &:appellant_tz + + attribute :appellant_relationship, &:appellant_relationship + + attribute :has_poa do |appeal| + appeal.claimant&.power_of_attorney + end + + attribute :cavc_remand do |object| + if object.cavc_remand + WorkQueue::CavcRemandSerializer.new(object.cavc_remand).serializable_hash[:data][:attributes] + end + end + + attribute :show_post_cavc_stream_msg do |object| + cavc_remand = CavcRemand.find_by(source_appeal_id: object.id) + cavc_remand.present? && cavc_remand.cavc_remands_appellant_substitution.present? + end + attribute :veteran_death_date attribute :veteran_file_number @@ -77,6 +124,14 @@ class WorkQueue::AppealSearchSerializer object.veteran ? object.veteran.id : nil end + attribute :document_id do |object| + object.latest_attorney_case_review&.document_id + end + + attribute :attorney_case_review_id do |object| + object.latest_attorney_case_review&.id + end + attribute :docket_switch do |object| if object.docket_switch WorkQueue::DocketSwitchSerializer.new(object.docket_switch).serializable_hash[:data][:attributes] diff --git a/db/schema.rb b/db/schema.rb index 0f0b73041ba..1de2cb0944b 100644 --- a/db/schema.rb +++ b/db/schema.rb @@ -10,7 +10,7 @@ # # It's strongly recommended that you check this file into your version control system. -ActiveRecord::Schema.define(version: 2023_11_29_224254) do +ActiveRecord::Schema.define(version: 2023_10_16_132819) do # These are extensions that must be enabled in order to support this database enable_extension "plpgsql" From c3c3be23658b24ab686f3e46b48715c05e7503e5 Mon Sep 17 00:00:00 2001 From: 631583 Date: Wed, 13 Dec 2023 08:24:57 -0800 Subject: [PATCH 17/20] fix spec, appeals serializer assgined_to_location if distributed to judge check --- app/models/serializers/work_queue/appeal_serializer.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/models/serializers/work_queue/appeal_serializer.rb b/app/models/serializers/work_queue/appeal_serializer.rb index 4bbd4cf6f0b..e32992e7663 100644 --- a/app/models/serializers/work_queue/appeal_serializer.rb +++ b/app/models/serializers/work_queue/appeal_serializer.rb @@ -104,7 +104,7 @@ class WorkQueue::AppealSerializer attribute :veteran_appellant_deceased, &:veteran_appellant_deceased? attribute :assigned_to_location do |object, params| - if object&.distributed_to_a_judge? + if object&.status&.status == :distributed_to_judge if (params[:user]&.judge? || params[:user]&.attorney? || User.list_hearing_coordinators.include?(params[:user])) object.assigned_to_location end From e62350d02ee5fbdfd653496be5561817534f6d12 Mon Sep 17 00:00:00 2001 From: 631583 Date: Thu, 14 Dec 2023 12:10:23 -0800 Subject: [PATCH 18/20] add specs to check css_id is only displayed to correct users --- .../work_queue/appeal_serializer.rb | 2 +- spec/fixes/assigned_to_search_results_spec.rb | 68 +++++++++++++++++++ 2 files changed, 69 insertions(+), 1 deletion(-) diff --git a/app/models/serializers/work_queue/appeal_serializer.rb b/app/models/serializers/work_queue/appeal_serializer.rb index e32992e7663..62409533333 100644 --- a/app/models/serializers/work_queue/appeal_serializer.rb +++ b/app/models/serializers/work_queue/appeal_serializer.rb @@ -105,7 +105,7 @@ class WorkQueue::AppealSerializer attribute :assigned_to_location do |object, params| if object&.status&.status == :distributed_to_judge - if (params[:user]&.judge? || params[:user]&.attorney? || User.list_hearing_coordinators.include?(params[:user])) + if params[:user]&.judge? || params[:user]&.attorney? || User.list_hearing_coordinators.include?(params[:user]) object.assigned_to_location end else diff --git a/spec/fixes/assigned_to_search_results_spec.rb b/spec/fixes/assigned_to_search_results_spec.rb index 3d0e3414fbb..82942c12713 100644 --- a/spec/fixes/assigned_to_search_results_spec.rb +++ b/spec/fixes/assigned_to_search_results_spec.rb @@ -71,4 +71,72 @@ expect(appeal.root_task.status).to eq "completed" end end + + context "appeal status is distributed to judge" do + let!(:appeal) { create(:appeal, :assigned_to_judge) } + let!(:default_user) { create(:default_user) } + let!(:hearings_coordinator_user) do + coordinator = create(:hearings_coordinator) + HearingsManagement.singleton.add_user(coordinator) + coordinator + end + let!(:attorney) do + attorney = create(:user) + create(:staff, :attorney_role, sdomainid: attorney.css_id) + attorney + end + let!(:judge) do + judge = create(:user) + create(:staff, :judge_role, sdomainid: judge.css_id) + judge + end + + before do + allow_any_instance_of(BGSService).to receive(:fetch_file_number_by_ssn) + .with(appeal.veteran.ssn.to_s) + .and_return(appeal.veteran.file_number) + end + context "user is not an attorney, judge, or hearing coordinator" do + scenario "current user is a system admin" do + visit "/search?veteran_ids=#{appeal.veteran.id}" + expect(appeal.status.status).to eq :distributed_to_judge + expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to + expect(page).not_to have_content("BVAAABSHIRE") # but css_id is not displeyed in the page + end + + scenario "current user is a default user" do + User.authenticate!(user: default_user) + visit "/search?veteran_ids=#{appeal.veteran.id}" + expect(appeal.status.status).to eq :distributed_to_judge + expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to + expect(page).not_to have_content("BVAAABSHIRE") # but css_id is not displeyed in the page + end + end + + context "user is an attorney, a judge, or a hearing coordinator" do + scenario "user is an attorney" do + User.authenticate!(user: attorney) + visit "/search?veteran_ids=#{appeal.veteran.id}" + expect(appeal.status.status).to eq :distributed_to_judge + expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to + expect(page).to have_content("BVAAABSHIRE") # and css_id is displeyed in the page + end + + scenario "user is an judge" do + User.authenticate!(user: judge) + visit "/search?veteran_ids=#{appeal.veteran.id}" + expect(appeal.status.status).to eq :distributed_to_judge + expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to + expect(page).to have_content("BVAAABSHIRE") # and css_id is displeyed in the page + end + + scenario "user is an hearings coordinator" do + User.authenticate!(user: hearings_coordinator_user) + visit "/search?veteran_ids=#{appeal.veteran.id}" + expect(appeal.status.status).to eq :distributed_to_judge + expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to + expect(page).to have_content("BVAAABSHIRE") # and css_id is displeyed in the page + end + end + end end From de57a26d8a873e23bd24365de7dc61a3594f6924 Mon Sep 17 00:00:00 2001 From: 631583 Date: Fri, 15 Dec 2023 08:44:15 -0800 Subject: [PATCH 19/20] fix typo in comments --- spec/fixes/assigned_to_search_results_spec.rb | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/spec/fixes/assigned_to_search_results_spec.rb b/spec/fixes/assigned_to_search_results_spec.rb index 82942c12713..75765fdddd3 100644 --- a/spec/fixes/assigned_to_search_results_spec.rb +++ b/spec/fixes/assigned_to_search_results_spec.rb @@ -101,7 +101,7 @@ visit "/search?veteran_ids=#{appeal.veteran.id}" expect(appeal.status.status).to eq :distributed_to_judge expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to - expect(page).not_to have_content("BVAAABSHIRE") # but css_id is not displeyed in the page + expect(page).not_to have_content("BVAAABSHIRE") # but css_id is not displayed in the page end scenario "current user is a default user" do @@ -109,7 +109,7 @@ visit "/search?veteran_ids=#{appeal.veteran.id}" expect(appeal.status.status).to eq :distributed_to_judge expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to - expect(page).not_to have_content("BVAAABSHIRE") # but css_id is not displeyed in the page + expect(page).not_to have_content("BVAAABSHIRE") # but css_id is not displayed in the page end end @@ -119,7 +119,7 @@ visit "/search?veteran_ids=#{appeal.veteran.id}" expect(appeal.status.status).to eq :distributed_to_judge expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to - expect(page).to have_content("BVAAABSHIRE") # and css_id is displeyed in the page + expect(page).to have_content("BVAAABSHIRE") # and css_id is displayed in the page end scenario "user is an judge" do @@ -127,7 +127,7 @@ visit "/search?veteran_ids=#{appeal.veteran.id}" expect(appeal.status.status).to eq :distributed_to_judge expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to - expect(page).to have_content("BVAAABSHIRE") # and css_id is displeyed in the page + expect(page).to have_content("BVAAABSHIRE") # and css_id is displayed in the page end scenario "user is an hearings coordinator" do @@ -135,7 +135,7 @@ visit "/search?veteran_ids=#{appeal.veteran.id}" expect(appeal.status.status).to eq :distributed_to_judge expect(appeal.assigned_to_location).to eq "BVAAABSHIRE" # css_id is part of assigned_to - expect(page).to have_content("BVAAABSHIRE") # and css_id is displeyed in the page + expect(page).to have_content("BVAAABSHIRE") # and css_id is displayed in the page end end end From cc6bc61d0a97a9745f06df7d313e3abf19b7e44e Mon Sep 17 00:00:00 2001 From: AimanK Date: Mon, 18 Dec 2023 09:22:21 -0500 Subject: [PATCH 20/20] V2 AMA serializer commit --- .../work_queue/appeal_search_serializer.rb | 55 ------------------- client/app/queue/utils.js | 4 -- 2 files changed, 59 deletions(-) diff --git a/app/models/serializers/work_queue/appeal_search_serializer.rb b/app/models/serializers/work_queue/appeal_search_serializer.rb index ba754828dd3..d72ff4547a8 100644 --- a/app/models/serializers/work_queue/appeal_search_serializer.rb +++ b/app/models/serializers/work_queue/appeal_search_serializer.rb @@ -6,28 +6,6 @@ class WorkQueue::AppealSearchSerializer set_type :appeal - attribute :assigned_attorney - attribute :assigned_judge - - attribute :appellant_hearing_email_recipient do |object| - object.email_recipients.find_by(type: "AppellantHearingEmailRecipient") - end - attribute :representative_hearing_email_recipient do |object| - object.email_recipients.find_by(type: "RepresentativeHearingEmailRecipient") - end - - attribute :appellant_email_address do |object| - object.appellant ? object.appellant.email_address : "Cannot Find Appellant" - end - - attribute :current_user_email do |_, params| - params[:user]&.email - end - - attribute :current_user_timezone do |_, params| - params[:user]&.timezone - end - attribute :contested_claim, &:contested_claim? attribute :issues do |object| @@ -71,35 +49,10 @@ class WorkQueue::AppealSearchSerializer attribute :distributed_to_a_judge, &:distributed_to_a_judge? - attribute :appellant_is_not_veteran - attribute :appellant_full_name do |object| object.claimant&.name end - attribute :appellant_address do |object| - object.claimant&.address - end - - attribute :appellant_tz, &:appellant_tz - - attribute :appellant_relationship, &:appellant_relationship - - attribute :has_poa do |appeal| - appeal.claimant&.power_of_attorney - end - - attribute :cavc_remand do |object| - if object.cavc_remand - WorkQueue::CavcRemandSerializer.new(object.cavc_remand).serializable_hash[:data][:attributes] - end - end - - attribute :show_post_cavc_stream_msg do |object| - cavc_remand = CavcRemand.find_by(source_appeal_id: object.id) - cavc_remand.present? && cavc_remand.cavc_remands_appellant_substitution.present? - end - attribute :veteran_death_date attribute :veteran_file_number @@ -124,14 +77,6 @@ class WorkQueue::AppealSearchSerializer object.veteran ? object.veteran.id : nil end - attribute :document_id do |object| - object.latest_attorney_case_review&.document_id - end - - attribute :attorney_case_review_id do |object| - object.latest_attorney_case_review&.id - end - attribute :docket_switch do |object| if object.docket_switch WorkQueue::DocketSwitchSerializer.new(object.docket_switch).serializable_hash[:data][:attributes] diff --git a/client/app/queue/utils.js b/client/app/queue/utils.js index bb1e6868921..ba2f6605c68 100644 --- a/client/app/queue/utils.js +++ b/client/app/queue/utils.js @@ -547,8 +547,6 @@ export const prepareAppealForSearchStore = (appeals) => { issues ).length, docketNumber: appeal.attributes.docket_number, - assignedAttorney: appeal.attributes.assigned_attorney, - assignedJudge: appeal.attributes.assigned_judge, distributedToJudge: appeal.attributes.distributed_to_a_judge, veteranFullName: appeal.attributes.veteran_full_name, veteranFileNumber: appeal.attributes.veteran_file_number, @@ -562,8 +560,6 @@ export const prepareAppealForSearchStore = (appeals) => { accumulator[appeal.attributes.external_id] = { hearings: prepareAppealHearingsForStore(appeal), appellantFullName: appeal.attributes.appellant_full_name, - currentUserEmail: appeal.attributes.current_user_email, - currentUserTimezone: appeal.attributes.current_user_timezone, contestedClaim: appeal.attributes.contested_claim, assignedToLocation: appeal.attributes.assigned_to_location, veteranParticipantId: appeal.attributes.veteran_participant_id,