diff --git a/src/RealCV.Infrastructure/Jobs/ProcessCVCheckJob.cs b/src/RealCV.Infrastructure/Jobs/ProcessCVCheckJob.cs
index ee8efe0..f8127e9 100644
--- a/src/RealCV.Infrastructure/Jobs/ProcessCVCheckJob.cs
+++ b/src/RealCV.Infrastructure/Jobs/ProcessCVCheckJob.cs
@@ -398,8 +398,8 @@ public sealed class ProcessCVCheckJob
{
Category = FlagCategory.Education.ToString(),
Severity = FlagSeverity.Critical.ToString(),
- Title = "Diploma Mill Detected",
- Description = $"'{edu.ClaimedInstitution}' is a known diploma mill. {edu.VerificationNotes}",
+ Title = "Unaccredited Institution",
+ Description = $"'{edu.ClaimedInstitution}' was not found in accredited institutions databases. Manual verification recommended.",
ScoreImpact = -DiplomaMillPenalty
});
}
@@ -413,8 +413,8 @@ public sealed class ProcessCVCheckJob
{
Category = FlagCategory.Education.ToString(),
Severity = FlagSeverity.Warning.ToString(),
- Title = "Suspicious Institution",
- Description = $"'{edu.ClaimedInstitution}' has suspicious characteristics. {edu.VerificationNotes}",
+ Title = "Unrecognised Institution",
+ Description = $"'{edu.ClaimedInstitution}' was not found in recognised institutions databases. Manual verification recommended.",
ScoreImpact = -SuspiciousInstitutionPenalty
});
}
diff --git a/src/RealCV.Infrastructure/Services/EducationVerifierService.cs b/src/RealCV.Infrastructure/Services/EducationVerifierService.cs
index 26be4ba..41313ab 100644
--- a/src/RealCV.Infrastructure/Services/EducationVerifierService.cs
+++ b/src/RealCV.Infrastructure/Services/EducationVerifierService.cs
@@ -24,7 +24,7 @@ public sealed class EducationVerifierService : IEducationVerifierService
IsVerified = false,
IsDiplomaMill = true,
IsSuspicious = true,
- VerificationNotes = "Institution is on the diploma mill blacklist",
+ VerificationNotes = "Institution not found in accredited institutions database",
ClaimedStartDate = education.StartDate,
ClaimedEndDate = education.EndDate,
DatesArePlausible = true,
@@ -43,7 +43,7 @@ public sealed class EducationVerifierService : IEducationVerifierService
IsVerified = false,
IsDiplomaMill = false,
IsSuspicious = true,
- VerificationNotes = "Institution name contains suspicious patterns common in diploma mills",
+ VerificationNotes = "Institution not found in recognised institutions database",
ClaimedStartDate = education.StartDate,
ClaimedEndDate = education.EndDate,
DatesArePlausible = true,
diff --git a/src/RealCV.Web/Components/Pages/Report.razor b/src/RealCV.Web/Components/Pages/Report.razor
index 6fbe87c..63f963e 100644
--- a/src/RealCV.Web/Components/Pages/Report.razor
+++ b/src/RealCV.Web/Components/Pages/Report.razor
@@ -281,6 +281,100 @@
+
+ @if (_report.EducationVerifications.Count > 0)
+ {
+
+
+
+
+
+ @foreach (var edu in _report.EducationVerifications)
+ {
+
+
+ @if (edu.IsDiplomaMill)
+ {
+
+ }
+ else if (edu.IsSuspicious)
+ {
+
+ }
+ else if (edu.IsVerified)
+ {
+
+ }
+ else
+ {
+
+ }
+
+
+ @edu.ClaimedInstitution
+ @if (!string.IsNullOrEmpty(edu.MatchedInstitution) && !edu.ClaimedInstitution.Equals(edu.MatchedInstitution, StringComparison.OrdinalIgnoreCase))
+ {
+ Matched: @edu.MatchedInstitution
+ }
+ @if (!string.IsNullOrEmpty(edu.VerificationNotes))
+ {
+ @edu.VerificationNotes
+ }
+
+
+ @if (!string.IsNullOrEmpty(edu.ClaimedQualification) || !string.IsNullOrEmpty(edu.ClaimedSubject))
+ {
+ @(edu.ClaimedQualification ?? "") @(edu.ClaimedSubject ?? "")
+ }
+ else
+ {
+ —
+ }
+
+
+ @if (edu.ClaimedStartDate.HasValue || edu.ClaimedEndDate.HasValue)
+ {
+ @(edu.ClaimedStartDate?.ToString("yyyy") ?? "?") – @(edu.ClaimedEndDate?.ToString("yyyy") ?? "?")
+ }
+ else
+ {
+ —
+ }
+
+
+ @GetEducationStatusLabel(edu)
+
+
+ }
+
+
+
+ }
+
@@ -462,8 +556,13 @@
@foreach (var flag in infoFlags)
{
-
@flag.Title
-
@flag.Description
+
+
@GetInfoFlagIcon(flag.Title)
+
+
@flag.Title
+
@flag.Description
+
+
}
}
@@ -623,6 +722,13 @@
border-left-color: var(--realcv-primary);
}
+ .info-flag-icon {
+ flex-shrink: 0;
+ color: var(--realcv-primary);
+ opacity: 0.85;
+ margin-top: 2px;
+ }
+
.flag-title {
font-weight: 600;
margin-bottom: 0.25rem;
@@ -745,6 +851,122 @@
font-size: 0.8125rem;
}
+ /* Education List - Compact Row Layout */
+ .education-list {
+ border-top: 1px solid #e5e7eb;
+ }
+
+ .education-header {
+ display: grid;
+ grid-template-columns: 24px 1fr 1fr 100px 90px;
+ gap: 0.5rem;
+ padding: 0.5rem 0.75rem;
+ background-color: #f8fafc;
+ border-bottom: 1px solid #e5e7eb;
+ font-size: 0.75rem;
+ font-weight: 600;
+ color: #475569;
+ text-transform: uppercase;
+ letter-spacing: 0.025em;
+ align-items: center;
+ }
+
+ .education-header div {
+ display: flex;
+ align-items: center;
+ }
+
+ .education-header div:nth-child(4),
+ .education-header div:nth-child(5) {
+ justify-content: center;
+ text-align: center;
+ }
+
+ .education-row {
+ display: grid;
+ grid-template-columns: 24px 1fr 1fr 100px 90px;
+ gap: 0.5rem;
+ align-items: center;
+ padding: 0.5rem 0.75rem;
+ border-bottom: 1px solid #e5e7eb;
+ transition: background-color 0.15s ease;
+ }
+
+ .education-row:hover {
+ background-color: #f9fafb;
+ }
+
+ .education-row-verified {
+ border-left: 3px solid #22c55e;
+ }
+
+ .education-row-unknown {
+ border-left: 3px solid #f59e0b;
+ }
+
+ .education-row-suspicious {
+ border-left: 3px solid #ef4444;
+ background-color: #fef2f2;
+ }
+
+ .education-row-diploma-mill {
+ border-left: 3px solid #dc2626;
+ background-color: #fef2f2;
+ }
+
+ .education-status-icon {
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ }
+
+ .education-institution {
+ display: flex;
+ flex-direction: column;
+ justify-content: center;
+ gap: 0.125rem;
+ min-width: 0;
+ }
+
+ .education-institution-name {
+ font-weight: 600;
+ font-size: 0.8125rem;
+ color: #1f2937;
+ }
+
+ .education-matched-name {
+ font-size: 0.75rem;
+ color: #059669;
+ font-style: italic;
+ }
+
+ .education-note-inline {
+ font-size: 0.75rem;
+ color: #4b5563;
+ line-height: 1.4;
+ }
+
+ .education-qualification {
+ font-size: 0.8125rem;
+ color: #4b5563;
+ }
+
+ .education-dates {
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ font-size: 0.8125rem;
+ color: #4b5563;
+ white-space: nowrap;
+ text-align: center;
+ }
+
+ .education-status {
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ }
+
/* Mobile Responsiveness */
@@media (max-width: 768px) {
.score-header .row {
@@ -800,6 +1022,37 @@
.employment-note-inline {
display: none;
}
+
+ .education-row {
+ grid-template-columns: 20px 1fr 70px;
+ gap: 0.25rem 0.5rem;
+ padding: 0.5rem;
+ }
+
+ .education-header {
+ grid-template-columns: 20px 1fr 70px;
+ }
+
+ .education-header div:nth-child(3),
+ .education-header div:nth-child(4) {
+ display: none;
+ }
+
+ .education-qualification {
+ display: none;
+ }
+
+ .education-dates {
+ display: none;
+ }
+
+ .education-note-inline {
+ display: none;
+ }
+
+ .education-matched-name {
+ display: none;
+ }
}
@@ -955,6 +1208,37 @@
};
}
+ private static string GetEducationRowClass(EducationVerificationResult edu)
+ {
+ if (edu.IsDiplomaMill) return "education-row-diploma-mill";
+ if (edu.IsSuspicious) return "education-row-suspicious";
+ if (edu.IsVerified) return "education-row-verified";
+ return "education-row-unknown";
+ }
+
+ private static string GetEducationStatusBadgeClass(EducationVerificationResult edu)
+ {
+ return edu.Status switch
+ {
+ "Recognised" => "bg-success",
+ "DiplomaMill" => "bg-danger",
+ "Suspicious" => "bg-danger",
+ _ => "bg-warning text-dark"
+ };
+ }
+
+ private static string GetEducationStatusLabel(EducationVerificationResult edu)
+ {
+ return edu.Status switch
+ {
+ "Recognised" => "Verified",
+ "DiplomaMill" => "Not Accredited",
+ "Suspicious" => "Unrecognised",
+ "Unknown" => "Unverified",
+ _ => edu.Status
+ };
+ }
+
private static string FormatFlagTitle(string title)
{
// Convert variable-style names to readable sentences
@@ -972,6 +1256,42 @@
};
}
+ private static MarkupString GetInfoFlagIcon(string title)
+ {
+ var icon = title switch
+ {
+ // Career timeline icons
+ "Career Span" => """
""",
+ "Employment Gap" => """
""",
+ "Concurrent Employment" => """
""",
+ "Average Tenure" or "Frequent Job Changes" => """
""",
+
+ // Employment status icons
+ "Current Status" => """
""",
+ "Long Tenure" => """
""",
+
+ // Leadership & experience icons
+ "Management Experience" => """
""",
+ "Individual Contributor" => """
""",
+ "Director Experience" => """
""",
+ "Public Company Experience" => """
""",
+
+ // Company & trajectory icons
+ "Company Size Pattern" => """
""",
+
+ // Education icons
+ "Unverified Institution" => """
""",
+
+ // Default - career trajectory or generic
+ _ when title.StartsWith("Career Trajectory") => """
""",
+
+ // Fallback generic info icon
+ _ => """
"""
+ };
+
+ return new MarkupString(icon);
+ }
+
// Lookup for first occurrence of each sequential group of the same company (pre-computed when report loads)
private HashSet
_firstOccurrenceIndices = new();