Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions src/linkup/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
LinkupFetchUrlIsFileError,
LinkupInsufficientCreditError,
LinkupInvalidRequestError,
LinkupIpNotWhitelistedError,
LinkupNoResultError,
LinkupPaymentRequiredError,
LinkupTaskNotFoundError,
Expand Down Expand Up @@ -58,6 +59,7 @@
FetchUrlIsFileError = LinkupFetchUrlIsFileError
InsufficientCreditError = LinkupInsufficientCreditError
InvalidRequestError = LinkupInvalidRequestError
IpNotWhitelistedError = LinkupIpNotWhitelistedError
NoResultError = LinkupNoResultError
PaymentRequiredError = LinkupPaymentRequiredError
ResearchTask = LinkupResearchTask
Expand Down Expand Up @@ -98,6 +100,7 @@
"FetchUrlIsFileError",
"InsufficientCreditError",
"InvalidRequestError",
"IpNotWhitelistedError",
"JSONObject",
"LinkupAuthenticationError",
"LinkupBudgetLimitExceededError",
Expand All @@ -113,6 +116,7 @@
"LinkupFetchUrlIsFileError",
"LinkupInsufficientCreditError",
"LinkupInvalidRequestError",
"LinkupIpNotWhitelistedError",
"LinkupNoResultError",
"LinkupPaymentRequiredError",
"LinkupResearchTask",
Expand Down
7 changes: 7 additions & 0 deletions src/linkup/_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
LinkupFetchUrlIsFileError,
LinkupInsufficientCreditError,
LinkupInvalidRequestError,
LinkupIpNotWhitelistedError,
LinkupNoResultError,
LinkupPaymentRequiredError,
LinkupTaskNotFoundError,
Expand Down Expand Up @@ -1361,6 +1362,12 @@ def _raise_linkup_error(self, response: httpx.Response) -> None:
f"Original error message: {error_msg}."
)
if response.status_code == 403:
if code == "IP_NOT_WHITELISTED":
raise LinkupIpNotWhitelistedError(
"The Linkup API rejected the request IP address (403). Make sure it is "
"included in the API key's IP whitelist.\n"
f"Original error message: {error_msg}."
)
if code == "TASK_TYPE_NOT_SUPPORTED":
raise LinkupUnsupportedTaskTypeError(
"The Linkup API returned an unsupported task type error (403). \n"
Expand Down
6 changes: 6 additions & 0 deletions src/linkup/_errors.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,12 @@ class LinkupAuthenticationError(Exception):
pass


class LinkupIpNotWhitelistedError(Exception):
"""IP whitelist error, raised when the request IP is not allowed by the API key."""

pass


class LinkupPaymentRequiredError(Exception):
"""Payment required error, raised when the Linkup API returns a 402 status code.

Expand Down
13 changes: 13 additions & 0 deletions tests/unit/client_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -474,6 +474,19 @@ async def test_async_search_structured_output_requires_schema(client: linkup.Cli
""",
linkup.AuthenticationError,
),
(
403,
b"""
{
"error": {
"code": "IP_NOT_WHITELISTED",
"message": "IP address 192.0.2.1 is not whitelisted",
"details": []
}
}
""",
linkup.IpNotWhitelistedError,
),
(
403,
b"""
Expand Down
Loading