feat(workspace): refine career workflows
Make job/CV comparisons language-aware and filter recruitment noise. Improve responsive career navigation, shared spacing, dashboard priorities, settings, localized workspace controls, and portable browser tests.
This commit is contained in:
@@ -51,7 +51,11 @@ public sealed record CareerMatchDto(
|
||||
IReadOnlyList<string> Suggestions,
|
||||
int AiSuggestionCount,
|
||||
bool HasSelectedCv = false,
|
||||
string? SelectedCvName = null);
|
||||
string? SelectedCvName = null,
|
||||
string JobLanguage = "en",
|
||||
string? CvLanguage = null,
|
||||
bool LanguageMismatch = false,
|
||||
bool UsedTranslatedJobDescription = false);
|
||||
|
||||
public interface IApplicationIntelligenceService
|
||||
{
|
||||
@@ -259,7 +263,24 @@ public sealed class ApplicationIntelligenceService : IApplicationIntelligenceSer
|
||||
["Skills"] = skillsText,
|
||||
};
|
||||
|
||||
var result = _match.Evaluate(job.JobTitle, job.Description ?? string.Empty, sections);
|
||||
var cvCorpus = string.Join("\n", sections.Values);
|
||||
var jobLanguage = NormalizeMatchLanguage(job.DescriptionLanguage, job.Description);
|
||||
var cvLanguage = NormalizeMatchLanguage(settings.Language, cvCorpus);
|
||||
var languageMismatch = !string.Equals(jobLanguage, cvLanguage, StringComparison.OrdinalIgnoreCase);
|
||||
|
||||
// Imported Norwegian adverts may already carry a trusted English translation. When the
|
||||
// explicitly linked CV is English, compare against that saved translation instead of
|
||||
// penalising equivalent wording in different languages. This endpoint remains read-only:
|
||||
// it never starts a translation request or mutates either source document.
|
||||
var useTranslatedJobDescription = languageMismatch
|
||||
&& jobLanguage == "nb"
|
||||
&& cvLanguage == "en"
|
||||
&& !string.IsNullOrWhiteSpace(job.TranslatedDescription);
|
||||
var matchDescription = useTranslatedJobDescription
|
||||
? job.TranslatedDescription!
|
||||
: job.Description ?? string.Empty;
|
||||
|
||||
var result = _match.Evaluate(job.JobTitle, matchDescription, sections);
|
||||
|
||||
var relevantExperience = experiences
|
||||
.Select(e => new { Entry = e, Override = Override(settings, e.ItemKey) })
|
||||
@@ -297,7 +318,11 @@ public sealed class ApplicationIntelligenceService : IApplicationIntelligenceSer
|
||||
Suggestions: Suggestions(result, relevantExperience.Count),
|
||||
AiSuggestionCount: aiCount,
|
||||
HasSelectedCv: true,
|
||||
SelectedCvName: attached.Name);
|
||||
SelectedCvName: attached.Name,
|
||||
JobLanguage: jobLanguage,
|
||||
CvLanguage: cvLanguage,
|
||||
LanguageMismatch: languageMismatch,
|
||||
UsedTranslatedJobDescription: useTranslatedJobDescription);
|
||||
}
|
||||
|
||||
// Suggestions describe what the USER could change. They never edit anything themselves.
|
||||
@@ -411,4 +436,16 @@ public sealed class ApplicationIntelligenceService : IApplicationIntelligenceSer
|
||||
|
||||
private static string? Blank(string? value) =>
|
||||
string.IsNullOrWhiteSpace(value) ? null : value.Trim();
|
||||
|
||||
private static string NormalizeMatchLanguage(string? declaredLanguage, string? text)
|
||||
{
|
||||
var language = string.IsNullOrWhiteSpace(declaredLanguage)
|
||||
? LanguageDetector.Detect(text)
|
||||
: declaredLanguage.Trim().ToLowerInvariant();
|
||||
return language.StartsWith("nb", StringComparison.Ordinal)
|
||||
|| language.StartsWith("no", StringComparison.Ordinal)
|
||||
|| language.StartsWith("nn", StringComparison.Ordinal)
|
||||
? "nb"
|
||||
: "en";
|
||||
}
|
||||
}
|
||||
|
||||
@@ -80,7 +80,9 @@ namespace JobTrackerApi.Services
|
||||
"mot", "uten", "hvordan", "ingen", "din", "ditt", "blir", "samme", "hvilken", "hvilke",
|
||||
"erfaring", "erfaringer", "kvalifikasjoner", "arbeidsoppgaver", "stilling", "stillingen",
|
||||
"søker", "ser", "ønsker", "mulighet", "spennende", "arbeidsmiljø", "selskap", "bedrift", "kandidat",
|
||||
"relevant", "fordel", "gode", "dyktig", "sammen",
|
||||
"relevant", "fordel", "gode", "god", "godt", "dyktig", "sammen", "både", "del", "dnbs",
|
||||
"faglig", "faglige", "får", "få", "hos", "utvikling", "ansvar", "ansvarlig", "bidra",
|
||||
"tilbyr", "kollega", "kollegaer", "løsning", "løsninger",
|
||||
// Common source-page chrome and consent text must never become tailoring advice.
|
||||
"cookie", "cookies", "privacy", "terms", "conditions", "menu", "home", "login", "contact",
|
||||
"website", "settings", "navigation", "jobs", "apply", "application", "share", "save", "accept",
|
||||
|
||||
Reference in New Issue
Block a user