Skip to content

Commit

Permalink
Merge pull request #27 from EasyPost/add_user_carrier_account
Browse files Browse the repository at this point in the history
Add user carrier account
  • Loading branch information
victoryftw committed Aug 10, 2015
2 parents 254bd19 + 15925b8 commit 972862e
Show file tree
Hide file tree
Showing 7 changed files with 100 additions and 16 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG
@@ -1,3 +1,7 @@
=== 2.0.16 2015-08-10

* Added ability to interact with carrier accounts (full CRUD)

=== 2.0.15 2015-07-31

* Fixed bug with address verification url rendering
Expand Down
2 changes: 1 addition & 1 deletion VERSION
@@ -1 +1 @@
2.0.15
2.0.16
61 changes: 48 additions & 13 deletions easypost/__init__.py
Expand Up @@ -58,7 +58,7 @@ def __init__(self, message=None, http_status=None, http_body=None):
pass


def convert_to_easypost_object(response, api_key):
def convert_to_easypost_object(response, api_key, parent=None, name=None):
types = {
'Address': Address,
'ScanForm': ScanForm,
Expand All @@ -74,7 +74,8 @@ def convert_to_easypost_object(response, api_key):
'Pickup': Pickup,
'Order': Order,
'PickupRate': PickupRate,
'PostageLabel': PostageLabel
'PostageLabel': PostageLabel,
'CarrierAccount': CarrierAccount
}

prefixes = {
Expand All @@ -92,11 +93,12 @@ def convert_to_easypost_object(response, api_key):
'order': Order,
'pickup': Pickup,
'pickuprate': PickupRate,
'pl': PostageLabel
'pl': PostageLabel,
'ca': CarrierAccount
}

if isinstance(response, list):
return [convert_to_easypost_object(r, api_key) for r in response]
return [convert_to_easypost_object(r, api_key, parent) for r in response]
elif isinstance(response, dict):
response = response.copy()
cls_name = response.get('object', EasyPostObject)
Expand All @@ -107,7 +109,7 @@ def convert_to_easypost_object(response, api_key):
cls = prefixes.get(cls_id[0:cls_id.find('_')], EasyPostObject)
else:
cls = EasyPostObject
return cls.construct_from(response, api_key)
return cls.construct_from(response, api_key, parent, name)
else:
return response

Expand Down Expand Up @@ -259,7 +261,8 @@ def request_raw(self, method, url, params=None):
headers = {
'X-EasyPost-Client-User-Agent': json.dumps(ua),
'User-Agent': 'EasyPost/v2 PythonClient/%s' % VERSION,
'Authorization': 'Bearer %s' % my_api_key
'Authorization': 'Bearer %s' % my_api_key,
'Content-type': 'application/x-www-form-urlencoded'
}

if request_lib == 'urlfetch':
Expand Down Expand Up @@ -287,7 +290,7 @@ def requests_request(self, method, abs_url, headers, params):
if params:
abs_url = self.build_url(abs_url, params)
data = None
elif method == 'post':
elif method == 'post' or method == 'put':
data = self.encode(params)
else:
raise Error("Bug discovered: invalid request method: %s. "
Expand All @@ -304,7 +307,7 @@ def requests_request(self, method, abs_url, headers, params):

def urlfetch_request(self, method, abs_url, headers, params):
args = {}
if method == 'post':
if method == 'post' or method == 'put':
args['payload'] = self.encode(params)
elif method == 'get' or method == 'delete':
abs_url = self.build_url(abs_url, params)
Expand Down Expand Up @@ -339,14 +342,17 @@ def handle_api_error(self, http_status, http_body, response):


class EasyPostObject(object):
def __init__(self, easypost_id=None, api_key=None, **params):
def __init__(self, easypost_id=None, api_key=None, parent=None, name=None, **params):
self.__dict__['_values'] = set()
self.__dict__['_unsaved_values'] = set()
self.__dict__['_transient_values'] = set()
# python2.6 doesnt have {} syntax for sets
self.__dict__['_immutable_values'] = set(['api_key', 'id'])
self.__dict__['_retrieve_params'] = params

self.__dict__['_parent'] = parent
self.__dict__['_name'] = name

self.__dict__['api_key'] = api_key

if easypost_id:
Expand All @@ -358,6 +364,14 @@ def __setattr__(self, k, v):
if k not in self._immutable_values:
self._unsaved_values.add(k)

cur = self
cur_parent = self._parent
while cur_parent:
if cur._name:
cur_parent._unsaved_values.add(cur._name)
cur = cur_parent
cur_parent = cur._parent

def __getattr__(self, k):
try:
return self.__dict__[k]
Expand Down Expand Up @@ -394,8 +408,8 @@ def values(self):
return self._values.keys()

@classmethod
def construct_from(cls, values, api_key):
instance = cls(values.get('id'), api_key)
def construct_from(cls, values, api_key, parent=None, name=None):
instance = cls(values.get('id'), api_key, parent, name)
instance.refresh_from(values, api_key)
return instance

Expand All @@ -405,11 +419,21 @@ def refresh_from(self, values, api_key):
for k, v in six.iteritems(values):
if k in self._immutable_values:
continue
self.__dict__[k] = convert_to_easypost_object(v, api_key)
self.__dict__[k] = convert_to_easypost_object(v, api_key, self, k)
self._values.add(k)
self._transient_values.discard(k)
self._unsaved_values.discard(k)

def flatten_unsaved(self):
values = {}
for key in self._unsaved_values:
value = self.get(key)
values[key] = value

if type(value) is EasyPostObject:
values[key] = value.flatten_unsaved()
return values

def __repr__(self):
type_string = ''

Expand Down Expand Up @@ -526,8 +550,11 @@ def save(self):
params = {}
for k in self._unsaved_values:
params[k] = getattr(self, k)
if type(params[k]) is EasyPostObject:
params[k] = params[k].flatten_unsaved()
params = {self.class_name(): params}
url = self.instance_url()
response, api_key = requestor.request('post', url, params)
response, api_key = requestor.request('put', url, params)
self.refresh_from(response, api_key)

return self
Expand Down Expand Up @@ -778,3 +805,11 @@ class Event(Resource):
@classmethod
def receive(self, values):
return convert_to_easypost_object(json.loads(values), api_key)


class CarrierAccount(AllResource, CreateResource, UpdateResource, DeleteResource):
@classmethod
def types(cls, api_key=None):
requestor = Requestor(api_key)
response, api_key = requestor.request('get', "/carrier_types")
return convert_to_easypost_object(response, api_key)
2 changes: 1 addition & 1 deletion easypost/version.py
@@ -1 +1 @@
VERSION = '2.0.15'
VERSION = '2.0.16'
38 changes: 38 additions & 0 deletions example_carrier_account.py
@@ -0,0 +1,38 @@
import easypost
easypost.api_key = 'API KEY'

original_num_cas = len(easypost.CarrierAccount.all())

created_ca = easypost.CarrierAccount.create(
type="UpsAccount",
description="A test Ups Account",
reference="PythonClientUpsTestAccount",
credentials={
"account_number": "A1A1A1",
"user_id": "UPSDOTCOM_USERNAME",
"password": "UPSDOTCOM_PASSWORD",
"access_license_number": "UPS_ACCESS_LICENSE_NUMBER"})

caid = created_ca["id"]

retrieved_ca = easypost.CarrierAccount.retrieve(caid)
retrieved_ca.description = "An updated description for a test Ups Account"
retrieved_ca.credentials = {
"account_number": "B2B2B2B2",
"user_id": "UPSDOTCOM_USERNAME",
"password": "UPSDOTCOM_PASSWORD",
"access_license_number": "UPS_ACCESS_LICENSE_NUMBER"
}
retrieved_ca.save()

updated_ca = easypost.CarrierAccount.retrieve(caid)
updated_ca.credentials["account_number"] = "C3C3C3C3C3"
updated_ca.credentials["user_id"] = "A_NEW_UPS_USERNAME"
updated_ca.save()

reupdated_ca = easypost.CarrierAccount.retrieve(caid)

# You can call save() with no unsaved changes, but it does nothing
final_ca = reupdated_ca.save()

final_ca.delete()
7 changes: 7 additions & 0 deletions example_carrier_account_types.py
@@ -0,0 +1,7 @@
import easypost
easypost.api_key = 'API KEY'

types = easypost.CarrierAccount.types()

for carrier_type in types:
print carrier_type.type
2 changes: 1 addition & 1 deletion setup.py
Expand Up @@ -34,7 +34,7 @@
author_email='contact@easypost.com',
url='https://easypost.com/',
packages=['easypost'],
package_data={'easypost' : ['../VERSION']},
package_data={'easypost': ['../VERSION']},
install_requires=install_requires,
test_suite='test'
)

0 comments on commit 972862e

Please sign in to comment.