#5099 - Bypass Program Suspension Restriction: UI#5859
Conversation
- Added Chip Status based on Client Type for the Restriction Bypasses
- EOL formatting changed from CRLF to LF
- Fixed the failing e2e tests
- Fixed failing e2e tests
- Fixed the failing e2e tests
There was a problem hiding this comment.
Pull request overview
Extends the “application restriction bypass” feature so AEST users can bypass both student and institution restrictions, and updates the web UI to display/select restriction type (Student vs Institution) when creating/viewing bypasses.
Changes:
- Updated API/service contracts and logic to support bypassing institution restrictions in addition to student restrictions.
- Enhanced UI modal and supporting components to display restriction type and submit the new payload shape.
- Updated/added e2e tests for the new “available restrictions to bypass” and “bypass restriction” scenarios.
Reviewed changes
Copilot reviewed 18 out of 18 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| sources/packages/web/src/views/aest/institution/Restrictions.vue | Switched from RestrictionEntityType to RestrictedParty when passing restriction party type. |
| sources/packages/web/src/types/vuetify.ts | Modified shared SelectItemType to include restriction party type. |
| sources/packages/web/src/types/contracts/RestrictionContract.ts | Renamed enum RestrictionEntityType to RestrictedParty and fixed comment punctuation. |
| sources/packages/web/src/services/http/dto/ApplicationRestrictionBypass.dto.ts | Updated web DTOs to support both student/institution restrictions and new field names. |
| sources/packages/web/src/services/http/ApplicationRestrictionBypassApi.ts | Renamed API method and updated return type for available restrictions. |
| sources/packages/web/src/services/ApplicationRestrictionBypassService.ts | Renamed service method and updated types to align with API changes. |
| sources/packages/web/src/components/generic/StatusChipClientType.vue | New chip component to label restriction party type. |
| sources/packages/web/src/components/common/students/StudentRestrictions.vue | Updated imports/returned bindings for RestrictedParty. |
| sources/packages/web/src/components/aest/students/bypassedRestrictions/BypassRestrictionModal.vue | Updated modal to select restriction + show party type chip; updated payload fields. |
| sources/packages/backend/libs/sims-db/src/entities/institution-restriction.model.ts | Added relation from institution restriction to application restriction bypasses. |
| sources/packages/backend/apps/api/src/services/application-restriction-bypass/application-restriction-bypass.service.ts | Added institution restriction support in option listing and bypass creation validations/persistence. |
| sources/packages/backend/apps/api/src/services/application-restriction-bypass/application-restriction-bypass.models.ts | Updated internal models to be restriction-party aware. |
| sources/packages/backend/apps/api/src/route-controllers/application-restriction-bypass/models/application-restriction-bypass.dto.ts | Updated API DTOs for new payload/response shapes including restriction party type. |
| sources/packages/backend/apps/api/src/route-controllers/application-restriction-bypass/application-restriction-bypass.aest.controller.ts | Updated endpoints/response mapping and error handling for institution restrictions. |
| sources/packages/backend/apps/api/src/route-controllers/application-restriction-bypass/tests/e2e/application-restriction-bypass.aest.controller.getAvailableRestricitionsToBypass.e2e-spec.ts | Expanded e2e coverage for listing available restrictions, including institution restrictions. |
| sources/packages/backend/apps/api/src/route-controllers/application-restriction-bypass/tests/e2e/application-restriction-bypass.aest.controller.getApplicationRestrictionBypass.e2e-spec.ts | Updated assertions for new response shape (restrictionId, restrictionType). |
| sources/packages/backend/apps/api/src/route-controllers/application-restriction-bypass/tests/e2e/application-restriction-bypass.aest.controller.bypassRestriction.e2e-spec.ts | Added institution restriction bypass creation and error scenarios. |
| sources/packages/backend/apps/api/src/constants/error-code.constants.ts | Added new error codes for institution restriction bypass scenarios. |
Comments suppressed due to low confidence (1)
sources/packages/backend/apps/api/src/route-controllers/application-restriction-bypass/tests/e2e/application-restriction-bypass.aest.controller.getAvailableRestricitionsToBypass.e2e-spec.ts:30
- Test file name contains a typo (
getAvailableRestricitionsToBypass) and does not match the project’s e2e naming convention ([feature].[client-type].controller.[method].e2e-spec.ts) or the controller method namegetAvailableRestrictionsToBypass. Please rename the file to keep conventions consistent and make tests easier to locate.
describe("ApplicationRestrictionBypassAESTController(e2e)-getAvailableRestrictionsToBypass.", () => {
let app: INestApplication;
let db: E2EDataSources;
sources/packages/web/src/components/common/students/StudentRestrictions.vue
Show resolved
Hide resolved
...controllers/application-restriction-bypass/application-restriction-bypass.aest.controller.ts
Show resolved
Hide resolved
| if (institutionApplication) { | ||
| const bypassedInstitutionRestrictionIds = new Set( | ||
| institutionApplication.currentAssessment.offering.institutionLocation.institution.restrictions | ||
| .flatMap( | ||
| (institutionRestriction) => | ||
| institutionRestriction.applicationRestrictionBypasses, | ||
| ) | ||
| .filter((bypass) => bypass.isActive) | ||
| .map((bypass) => bypass.institutionRestriction.id), | ||
| ); | ||
|
|
||
| return studentRestrictionsThatAreNotBypassed | ||
| .filter((studentRestriction) => | ||
| allowedRestrictionActions.some((actionType) => | ||
| studentRestriction.restriction.actionType.includes(actionType), | ||
| ), | ||
| ) | ||
| .map((studentRestriction) => ({ | ||
| studentRestrictionId: studentRestriction.id, | ||
| restrictionCode: studentRestriction.restriction.restrictionCode, | ||
| studentRestrictionCreatedAt: studentRestriction.createdAt, | ||
| })) | ||
| .sort((a, b) => a.restrictionCode.localeCompare(b.restrictionCode)); | ||
| const institutionRestrictionsThatAreNotBypassed = | ||
| institutionApplication.currentAssessment.offering.institutionLocation.institution.restrictions.filter( | ||
| (institutionRestriction) => | ||
| !bypassedInstitutionRestrictionIds.has(institutionRestriction.id), | ||
| ); | ||
| mappedInstitutionRestrictionsNotBypassed = | ||
| institutionRestrictionsThatAreNotBypassed.map( | ||
| (institutionRestriction) => ({ | ||
| restrictionId: institutionRestriction.id, | ||
| restrictionCode: institutionRestriction.restriction.restrictionCode, | ||
| restrictionCreatedAt: institutionRestriction.createdAt, | ||
| restrictionType: RestrictedParty.Institution, | ||
| }), | ||
| ); |
There was a problem hiding this comment.
Institution restrictions are currently returned as bypass options without filtering by the allowed restriction action types for the application’s offering intensity (unlike student restrictions, which are filtered). If institution restrictions can include non-disbursement-blocking action types, this will expose/allow bypasses that should not be available. Consider applying the same allowedRestrictionActions filter using institutionRestriction.restriction.actionType (the query already selects actionType).
...es/packages/web/src/components/aest/students/bypassedRestrictions/BypassRestrictionModal.vue
Outdated
Show resolved
Hide resolved
- Addressed the copilot review comments
sources/packages/backend/apps/api/src/constants/error-code.constants.ts
Outdated
Show resolved
Hide resolved
sources/packages/backend/apps/api/src/constants/error-code.constants.ts
Outdated
Show resolved
Hide resolved
| const remitRestriction = await db.restriction.findOne({ | ||
| where: { | ||
| restrictionCode: RestrictionCode.REMIT, | ||
| }, | ||
| }); |
There was a problem hiding this comment.
Remit restriction must technically not be valid to create a bypass as it does not block disbursement.
I believe there is an existing GAP in API not validating the restriction actions while creating bypass.
...ass/_tests_/e2e/application-restriction-bypass.aest.controller.bypassRestriction.e2e-spec.ts
Outdated
Show resolved
Hide resolved
...ass/_tests_/e2e/application-restriction-bypass.aest.controller.bypassRestriction.e2e-spec.ts
Outdated
Show resolved
Hide resolved
...ass/_tests_/e2e/application-restriction-bypass.aest.controller.bypassRestriction.e2e-spec.ts
Outdated
Show resolved
Hide resolved
...ass/_tests_/e2e/application-restriction-bypass.aest.controller.bypassRestriction.e2e-spec.ts
Outdated
Show resolved
Hide resolved
...ass/_tests_/e2e/application-restriction-bypass.aest.controller.bypassRestriction.e2e-spec.ts
Outdated
Show resolved
Hide resolved
sources/packages/web/src/types/contracts/RestrictionBypassContracts.ts
Outdated
Show resolved
Hide resolved
|
Thanks for making the changes. Added few more comments. |
- Review Comments
- Review Comments
| * @returns allowed restriction actions. | ||
| */ | ||
| private getAllowedRestrictionActions( | ||
| offeringIntensity: string, |
There was a problem hiding this comment.
Please use the type OfferingIntensity
| RestrictionActionType.StopPartTimeDisbursement, | ||
| ]; | ||
| default: | ||
| return []; |
There was a problem hiding this comment.
Please throw error on default. throw new Error("Invalid offering intensity.")
| }) | ||
| bypassRemovedDate?: Date; | ||
|
|
||
| getBypassRestriction(): StudentRestriction | InstitutionRestriction { |
There was a problem hiding this comment.
Please add comments to the method. Same for other method as well.
| if (this.studentRestriction && this.institutionRestriction) { | ||
| throw new Error( | ||
| "Cannot have both student restriction and institution restriction associated with a restriction bypass.", | ||
| ); | ||
| } |
There was a problem hiding this comment.
This condition is not necessary as both restrictions cannot co-exist in DB together.
dheepak-aot
left a comment
There was a problem hiding this comment.
Thanks for making the changes and addressing the validation missing for action types on bypass create. Looks good. Added few last comments to wrap up.
- Review Comments
|
| @@ -0,0 +1,16 @@ | |||
| <template> | |||
There was a problem hiding this comment.
| import { computed } from "vue"; | ||
|
|
||
| const props = defineProps<{ | ||
| clientType: RestrictedParty.Student | RestrictedParty.Institution; |
There was a problem hiding this comment.
FYI clientType is still being used but as suggested I think we can just use ChipTag.vue in which case this won't matter.




As a part of this PR, the following was completed:
History of Bypassed Restrictions:
Bypass Restriction Modal Dialog:
Bypassed Institution Restriction View:
Added / Updated the following e2e tests:
ApplicationRestrictionBypassAESTController(e2e)-getAvailableRestrictionsToBypass.
√ Should list all the active restrictions and not the ones already bypassed for a part-time application when there are some restrictions bypassed and some others not.
ApplicationRestrictionBypassAESTController(e2e)-bypassRestriction
√ Should be able to create a bypass when there is not an active bypass for the same institution restriction.
√ Should throw an HTTP error while creating a bypass when there is an active bypass for the same active institution restriction.
√ Should throw an HTTP error while creating a bypass when institution restriction is not active.
ApplicationRestrictionBypassAESTController(e2e)-getApplicationRestrictionBypass.
√ Should get an institution application restriction bypass for a submitted part-time application when there is an application restriction bypass with the required id.