Feature/examination access decision#32
Open
Soldier224K wants to merge 3 commits into
Open
Conversation
added 3 commits
May 23, 2026 19:35
- Add reviewer_id, review_timestamp, review_reason to ConflictAlert
- Add get_conflict_details() to inspect prior face history
- Add admin_review_conflict() for approval/rejection actions
- Add get_override_log() to persist manual review decisions
- Add API endpoints: /face/conflict/{id}, /admin/review-conflict, /admin/override-log
- Add new event types: ADMIN_REVIEW_STARTED, ADMIN_REVIEW_APPROVED, ADMIN_REVIEW_REJECTED, ADMIN_OVERRIDE_ACTION
- Add 5 new tests for admin review functionality
- Add AuditLogService for comprehensive identity event logging
- Log verification attempts, face matches/mismatches, suspicious events
- Log admin override actions and examination access decisions
- Add get_timeline() for roll-number or session filtered audit trails
- Add search() for querying audit log content
- Add new event types: VERIFICATION_ATTEMPT, FACE_MATCH, FACE_MISMATCH, SUSPICIOUS_IDENTITY, ADMIN_OVERRIDE, EXAMINATION_ACCESS
- Add API endpoints: /audit/timeline, /audit/search, /audit/events/{type}
- Add 15 tests covering all audit logging functionality
- Add ExaminationAccessDecision for producing access decisions before viva - Support ACCESS_GRANTED, ACCESS_DENIED, MANUAL_REVIEW_REQUIRED, TEMPORARY_BLOCK outcomes - Aggregate verification outputs, identity conflict results, safety checks - Generate explainable access decisions with evidence - Issue secure examination authorization with decision IDs - Add 12 tests covering all decision outcomes and flow scenarios
Contributor
There was a problem hiding this comment.
Pull request overview
This PR adds administrative review metadata to face-detection conflict alerts, introduces an in-memory audit logging service with API endpoints to query it, and adds an examination access decision engine with corresponding tests.
Changes:
- Extend
ConflictAlertwith reviewer metadata and add conflict-detail/admin-review/override-log helper APIs inFaceDetectionService. - Add
AuditLogService+AuditEventand expose audit query endpoints in the FastAPI app. - Add
ExaminationAccessDecisiondecision engine (verification/conflict/safety-check driven) with unit tests.
Reviewed changes
Copilot reviewed 8 out of 8 changed files in this pull request and generated 10 comments.
Show a summary per file
| File | Description |
|---|---|
| backend/src/services/face_detection.py | Adds reviewer fields to alerts and new conflict/admin review helper methods. |
| backend/src/services/audit_log.py | Introduces an in-memory audit log service and event model. |
| backend/src/services/access_decision.py | Adds the examination access decision engine and supporting data models. |
| backend/src/main.py | Wires in new admin/audit endpoints and extends resolve-alert request schema. |
| backend/src/models/events.py | Adds new EventType constants for admin/audit-related events. |
| backend/tests/test_face_detection.py | Updates/extends face-detection tests for reviewer metadata and new APIs. |
| backend/tests/test_audit_log.py | Adds unit tests for the new audit log service. |
| backend/tests/test_access_decision.py | Adds unit tests for the examination access decision engine. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Comment on lines
+82
to
+86
| async def get_conflict_details(conflict_id: str): | ||
| details = face_service.get_conflict_details(conflict_id) | ||
| if details is None: | ||
| return {"error": "Conflict not found"}, 404 | ||
| return details |
Comment on lines
+90
to
+98
| success = face_service.admin_review_conflict( | ||
| request.conflict_id, | ||
| request.approved, | ||
| request.reviewer_id, | ||
| request.reason | ||
| ) | ||
| if not success: | ||
| return {"error": "Conflict not found"}, 404 | ||
| return {"success": True, "message": "Review decision recorded"} |
Comment on lines
+46
to
+50
| event = AuditEvent( | ||
| event_id=self._generate_event_id(roll_number, "verification_attempt", datetime.now(timezone.utc)), | ||
| timestamp=datetime.now(timezone.utc), | ||
| event_type="verification_attempt", | ||
| roll_number=roll_number, |
| @@ -0,0 +1,201 @@ | |||
| from typing import Optional, List, Dict, Any | |||
| from dataclasses import dataclass, field | |||
Comment on lines
+152
to
+156
| def get_decisions_for_roll(self, roll_number: str) -> List[AccessDecisionResult]: | ||
| return [ | ||
| d for d in self._decisions.values() | ||
| if roll_number in str(d.evidence.get("verification", {})) | ||
| ] |
Comment on lines
+181
to
+188
| for alert in self.alerts: | ||
| if alert.conflict_id == conflict_id: | ||
| alert.status = "approved" if approved else "rejected" | ||
| alert.reviewer_id = reviewer_id | ||
| alert.review_timestamp = datetime.now(timezone.utc) | ||
| alert.review_reason = reason | ||
| return True | ||
| return False |
Comment on lines
+1
to
+5
| import pytest | ||
| from backend.src.services.audit_log import ( | ||
| AuditLogService, | ||
| AuditEvent, | ||
| ) |
|
|
||
| def test_deterministic_event_id(self): | ||
| log = AuditLogService() | ||
| import time |
| @@ -0,0 +1,238 @@ | |||
| import pytest | |||
Comment on lines
+104
to
+113
| @app.get("/audit/timeline") | ||
| async def get_audit_timeline(roll_number: Optional[str] = None, session_id: Optional[str] = None): | ||
| result = [] | ||
| if session_id: | ||
| result = audit_log.get_session_timeline(session_id) | ||
| elif roll_number: | ||
| result = audit_log.get_timeline(roll_number) | ||
| else: | ||
| result = audit_log.get_timeline() | ||
| return result |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
closes #20