Skip to content

Commit e916406

Browse files
authoredJan 26, 2023
Merge pull request #257 from EasyPost/stateless_rates
feat: add retrieve_stateless_rates function
2 parents 062909b + a2a930d commit e916406

7 files changed

+297
-1
lines changed
 

‎CHANGELOG.md

+5
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,10 @@
11
# CHANGELOG
22

3+
## Next Release
4+
5+
- Adds `retrieve_stateless_rates` function to pull stateless rates when shipment data is provided
6+
- Adds `get_lowest_stateless_rate` function to filter the lowest stateless rate
7+
38
## v7.9.0 (2023-01-18)
49

510
- Adds `all` function to `Pickup` to retrieve all pickups

‎easypost/beta/__init__.py

+1
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,3 @@
11
# flake8: noqa
2+
from easypost.beta.rate import Rate
23
from easypost.beta.referral import Referral

‎easypost/beta/rate.py

+26
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
from typing import (
2+
Any,
3+
Dict,
4+
Optional,
5+
)
6+
7+
from easypost.easypost_object import convert_to_easypost_object
8+
from easypost.requestor import (
9+
RequestMethod,
10+
Requestor,
11+
)
12+
from easypost.resource import Resource
13+
14+
15+
class Rate(Resource):
16+
@classmethod
17+
def retrieve_stateless_rates(cls, api_key: Optional[str] = None, **params) -> Dict[str, Any]:
18+
"""Retrieves stateless rates by passing shipment data."""
19+
requestor = Requestor(local_api_key=api_key)
20+
url = cls.class_url()
21+
wrapped_params = {
22+
"shipment": params,
23+
}
24+
response, api_key = requestor.request(method=RequestMethod.POST, url=url, params=wrapped_params, beta=True)
25+
26+
return convert_to_easypost_object(response=response.get("rates", None), api_key=api_key)

‎easypost/util.py

+31-1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
from typing import List
1+
from typing import (
2+
Any,
3+
Dict,
4+
List,
5+
)
26

37
from easypost.easypost_object import EasyPostObject
48
from easypost.error import Error
@@ -29,3 +33,29 @@ def get_lowest_object_rate(
2933
raise Error(message="No rates found.")
3034

3135
return lowest_rate
36+
37+
38+
def get_lowest_stateless_rate(
39+
stateless_rates: List[Dict[str, Any]], carriers: List[str] = None, services: List[str] = None
40+
) -> Dict[str, Any]:
41+
"""Get the lowest stateless rate."""
42+
carriers = carriers or []
43+
services = services or []
44+
lowest_rate = None
45+
46+
carriers = [carrier.lower() for carrier in carriers]
47+
services = [service.lower() for service in services]
48+
49+
for rate in stateless_rates:
50+
if (carriers and rate["carrier"].lower() not in carriers) or (
51+
services and rate["service"].lower() not in services
52+
):
53+
continue
54+
55+
if lowest_rate is None or float(rate.rate) < float(lowest_rate.rate):
56+
lowest_rate = rate
57+
58+
if lowest_rate is None:
59+
raise Error(message="No rates found.")
60+
61+
return lowest_rate

‎tests/cassettes/test_beta_get_lowest_stateless_rate.yaml

+105
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

‎tests/cassettes/test_beta_retrieve_stateless_rates.yaml

+107
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

‎tests/test_beta_rate.py

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
import pytest
2+
3+
import easypost
4+
from easypost.util import get_lowest_stateless_rate
5+
6+
7+
@pytest.mark.vcr()
8+
def test_beta_retrieve_stateless_rates(basic_shipment):
9+
"""Tests that we can retrieve stateless rates when basic shipment data."""
10+
stateless_rates = easypost.beta.Rate.retrieve_stateless_rates(**basic_shipment)
11+
12+
assert all(rate["object"] == "Rate" for rate in stateless_rates)
13+
14+
15+
@pytest.mark.vcr()
16+
def test_beta_get_lowest_stateless_rate(basic_shipment):
17+
"""Tests that we can return the lowest stateless rate from a list of stateless rates."""
18+
stateless_rates = easypost.beta.Rate.retrieve_stateless_rates(**basic_shipment)
19+
20+
lowest_stateless_rate = get_lowest_stateless_rate(stateless_rates)
21+
22+
assert lowest_stateless_rate["service"] == "First"

0 commit comments

Comments
 (0)