From 6b9a34c8e7c84f81b7f905c5a35eaf50ba7401c5 Mon Sep 17 00:00:00 2001 From: Nedhir Date: Fri, 16 May 2025 14:47:35 +0200 Subject: [PATCH] feat: add new upskilling endpoints for both profile and job and the text geocoding endpoint draft --- hrflow/core/validation.py | 5 +++ hrflow/job/__init__.py | 2 ++ hrflow/job/upskilling.py | 57 ++++++++++++++++++++++++++++++++++ hrflow/profile/__init__.py | 2 ++ hrflow/profile/upskilling.py | 59 ++++++++++++++++++++++++++++++++++++ hrflow/text/__init__.py | 2 ++ hrflow/text/geocoding.py | 34 +++++++++++++++++++++ 7 files changed, 161 insertions(+) create mode 100644 hrflow/job/upskilling.py create mode 100644 hrflow/profile/upskilling.py create mode 100644 hrflow/text/geocoding.py diff --git a/hrflow/core/validation.py b/hrflow/core/validation.py index 0c68472..0046d21 100644 --- a/hrflow/core/validation.py +++ b/hrflow/core/validation.py @@ -90,6 +90,11 @@ def validate_limit(value): return value +def validate_score(value): + if value < 0 or value > 1: + raise ValueError("score must be between 0 and 1") + + return value def validate_provider_keys(value): if not value or not all(isinstance(elt, str) for elt in value): diff --git a/hrflow/job/__init__.py b/hrflow/job/__init__.py index 75f792f..c65a089 100644 --- a/hrflow/job/__init__.py +++ b/hrflow/job/__init__.py @@ -6,6 +6,7 @@ from .scoring import JobScoring from .searching import JobSearching from .storing import JobStoring +from .upskilling import JobUpskilling class Job: @@ -19,3 +20,4 @@ def __init__(self, client): self.reasoning = JobReasoning(self.client) self.storing = JobStoring(self.client) self.matching = JobMatching(self.client) + self.upskilling = JobUpskilling(self.client) \ No newline at end of file diff --git a/hrflow/job/upskilling.py b/hrflow/job/upskilling.py new file mode 100644 index 0000000..57a703d --- /dev/null +++ b/hrflow/job/upskilling.py @@ -0,0 +1,57 @@ +import typing as t + +from ..core.rate_limit import rate_limiter +from ..core.validation import ( + + KEY_REGEX, + validate_key, + validate_response, + validate_score, +) +class JobUpskilling: + def __init__(self, api): + self.client = api + + @rate_limiter + def get( + self, + board_key: str, + job_key: str, + source_key: str, + profile_key: str, + score: float, + output_lang: str = "en", + ) -> t.Dict[str, t.Any]: + """ + 🧠Get the SWOT explaining a Job recommendation for a Profile. + (https://api.hrflow.ai/v1/job/upskilling) + Args: + source_key: + The key of the Source associated to the profile. + profile_key: + The Profile unique identifier. + board_key: + The key of the Board associated to the job. + job_key: + The Job unique identifier. + score: + Matching score of the Job according to the Profile. The Score value is between 0 and 1. + output_lang: + The language of the output. Default is 'en'. + + Returns: + `/job/upskilling` response + """ + + params = dict( + source_key=validate_key("Source", source_key, regex=KEY_REGEX), + profile_key=validate_key("Profile", profile_key, regex=KEY_REGEX), + board_key=validate_key("Board", board_key, regex=KEY_REGEX), + job_key=validate_key("Job", job_key, regex=KEY_REGEX), + score=validate_score(score), + output_lang=output_lang, + ) + + response = self.client.get("job/upskilling", query_params=params) + + return validate_response(response) \ No newline at end of file diff --git a/hrflow/profile/__init__.py b/hrflow/profile/__init__.py index 1f5016b..efb1aaf 100644 --- a/hrflow/profile/__init__.py +++ b/hrflow/profile/__init__.py @@ -12,6 +12,7 @@ from .searching import ProfileSearching from .storing import ProfileStoring from .unfolding import ProfileUnfolding +from .upskilling import ProfileUpskilling class Profile(object): @@ -39,3 +40,4 @@ def __init__(self, client): self.unfolding = ProfileUnfolding(self.client) self.matching = ProfileMatching(self.client) self.grading = ProfileGrading(self.client) + self.upskilling = ProfileUpskilling(self.client) diff --git a/hrflow/profile/upskilling.py b/hrflow/profile/upskilling.py new file mode 100644 index 0000000..dd9024a --- /dev/null +++ b/hrflow/profile/upskilling.py @@ -0,0 +1,59 @@ +import typing as t + +from ..core.rate_limit import rate_limiter +from ..core.validation import ( + + KEY_REGEX, + validate_key, + validate_response, + validate_score, +) + + +class ProfileUpskilling: + def __init__(self, api): + self.client = api + + @rate_limiter + def get( + self, + board_key: str, + job_key: str, + source_key: str, + profile_key: str, + score: float, + output_lang: str = "en", + ) -> t.Dict[str, t.Any]: + """ + 🧠Get the SWOT explaining a Profile recommendation for a Job. + (https://api.hrflow.ai/v1/profile/upskilling) + Args: + board_key: + The key of the Board associated to the job. + job_key: + The Job unique identifier. + source_key: + The key of the Source associated to the profile. + profile_key: + The Profile unique identifier. + score: + Matching score of the Profile according to the Job. The Score value is between 0 and 1. + output_lang: + The language of the output. Default is 'en'. + + Returns: + `/profile/upskilling` response + """ + + params = dict( + board_key=validate_key("Board", board_key, regex=KEY_REGEX), + job_key=validate_key("Job", job_key, regex=KEY_REGEX), + source_key=validate_key("Source", source_key, regex=KEY_REGEX), + profile_key=validate_key("Profile", profile_key, regex=KEY_REGEX), + score=validate_score(score), + output_lang=output_lang, + ) + + response = self.client.get("profile/upskilling", query_params=params) + + return validate_response(response) \ No newline at end of file diff --git a/hrflow/text/__init__.py b/hrflow/text/__init__.py index 2e242bd..a9e7843 100644 --- a/hrflow/text/__init__.py +++ b/hrflow/text/__init__.py @@ -1,6 +1,7 @@ """Profile related calls.""" from .embedding import TextEmbedding +from .geocoding import TextGeocoding from .imaging import TextImaging from .linking import TextLinking from .ocr import TextOCR @@ -29,3 +30,4 @@ def __init__(self, client): self.tagging = TextTagging(self.client) self.ocr = TextOCR(self.client) self.imaging = TextImaging(self.client) + self.geocoding = TextGeocoding(self.client) diff --git a/hrflow/text/geocoding.py b/hrflow/text/geocoding.py new file mode 100644 index 0000000..7181298 --- /dev/null +++ b/hrflow/text/geocoding.py @@ -0,0 +1,34 @@ +import typing as t + +from ..core.rate_limit import rate_limiter +from ..core.validation import validate_response + + +class TextGeocoding: + """Manage geocoding related calls.""" + + def __init__(self, api): + """Init.""" + self.client = api + + @rate_limiter + def post( + self, + texts: t.List[str], + ) -> t.Dict[str, t.Any]: + """ + Geocode a list of texts. + + Args: + texts: + Geocode a list of texts. Example: ["112 avenue charles de gaulle 92200 neuilly-sur-seine", "New York", "7 rue 4 septembre Paris"]. + + Returns: + `/text/geocoding` response + """ + payload = dict( + texts=texts, + ) + + response = self.client.post("text/geocoding", json=payload) + return validate_response(response) \ No newline at end of file