1212from SoftLayer import consts
1313from SoftLayer import transports
1414
15+ # pylint: disable=invalid-name
16+
17+
1518API_PUBLIC_ENDPOINT = consts .API_PUBLIC_ENDPOINT
1619API_PRIVATE_ENDPOINT = consts .API_PRIVATE_ENDPOINT
17- __all__ = ['Client' , 'API_PUBLIC_ENDPOINT' , 'API_PRIVATE_ENDPOINT' ]
18-
19- VALID_CALL_ARGS = set ([
20+ __all__ = [
21+ 'create_client_from_env' ,
22+ 'Client' ,
23+ 'BaseClient' ,
24+ 'API_PUBLIC_ENDPOINT' ,
25+ 'API_PRIVATE_ENDPOINT' ,
26+ ]
27+
28+ VALID_CALL_ARGS = set ((
2029 'id' ,
2130 'mask' ,
2231 'filter' ,
2534 'raw_headers' ,
2635 'limit' ,
2736 'offset' ,
28- ] )
37+ ) )
2938
3039
31- class Client (object ):
32- """A SoftLayer API client.
40+ def create_client_from_env (username = None ,
41+ api_key = None ,
42+ endpoint_url = None ,
43+ timeout = None ,
44+ auth = None ,
45+ config_file = None ,
46+ proxy = None ,
47+ user_agent = None ,
48+ transport = None ):
49+ """Creates a SoftLayer API client using your environment.
50+
51+ Settings are loaded via keyword arguments, environemtal variables and
52+ config file.
3353
3454 :param username: an optional API username if you wish to bypass the
3555 package's built-in username
@@ -51,38 +71,62 @@ class Client(object):
5171 Usage:
5272
5373 >>> import SoftLayer
54- >>> client = SoftLayer.Client(username="username", api_key="api_key" )
74+ >>> client = SoftLayer.create_client_from_env( )
5575 >>> resp = client['Account'].getObject()
5676 >>> resp['companyName']
5777 'Your Company'
5878
5979 """
80+ settings = config .get_client_settings (username = username ,
81+ api_key = api_key ,
82+ endpoint_url = endpoint_url ,
83+ timeout = timeout ,
84+ proxy = proxy ,
85+ config_file = config_file )
86+
87+ # Default the transport to use XMLRPC
88+ if transport is None :
89+ transport = transports .XmlRpcTransport (
90+ endpoint_url = settings .get ('endpoint_url' ),
91+ proxy = settings .get ('proxy' ),
92+ timeout = settings .get ('timeout' ),
93+ user_agent = user_agent ,
94+ )
95+
96+ # If we have enough information to make an auth driver, let's do it
97+ if auth is None and settings .get ('username' ) and settings .get ('api_key' ):
98+
99+ auth = slauth .BasicAuthentication (
100+ settings .get ('username' ),
101+ settings .get ('api_key' ),
102+ )
103+
104+ return BaseClient (auth = auth , transport = transport )
105+
106+
107+ def Client (** kwargs ):
108+ """Get a SoftLayer API Client using environmental settings.
109+
110+ Deprecated in favor of create_client_from_env()
111+ """
112+ warnings .warn ("use SoftLayer.create_client_from_env() instead" ,
113+ DeprecationWarning )
114+ return create_client_from_env (** kwargs )
115+
116+
117+ class BaseClient (object ):
118+ """Base SoftLayer API client.
119+
120+ :param auth: auth driver that looks like SoftLayer.auth.AuthenticationBase
121+ :param transport: An object that's callable with this signature:
122+ transport(SoftLayer.transports.Request)
123+ """
124+
60125 _prefix = "SoftLayer_"
61126
62- def __init__ (self , username = None , api_key = None , endpoint_url = None ,
63- timeout = None , auth = None , config_file = None , proxy = None ,
64- user_agent = None , transport = None ):
65-
66- settings = config .get_client_settings (username = username ,
67- api_key = api_key ,
68- endpoint_url = endpoint_url ,
69- timeout = timeout ,
70- auth = auth ,
71- proxy = proxy ,
72- config_file = config_file )
73- self .auth = settings .get ('auth' )
74-
75- self .endpoint_url = (settings .get ('endpoint_url' ) or
76- API_PUBLIC_ENDPOINT ).rstrip ('/' )
77- self .transport = transport or transports .XmlRpcTransport ()
78-
79- self .timeout = None
80- if settings .get ('timeout' ):
81- self .timeout = float (settings .get ('timeout' ))
82- self .proxy = None
83- if settings .get ('proxy' ):
84- self .proxy = settings .get ('proxy' )
85- self .user_agent = user_agent
127+ def __init__ (self , auth = None , transport = None ):
128+ self .auth = auth
129+ self .transport = transport
86130
87131 def authenticate_with_password (self , username , password ,
88132 security_question_id = None ,
@@ -145,13 +189,10 @@ def call(self, service, method, *args, **kwargs):
145189 raise TypeError (
146190 'Invalid keyword arguments: %s' % ',' .join (invalid_kwargs ))
147191
148- if not service .startswith (self ._prefix ):
192+ if self . _prefix and not service .startswith (self ._prefix ):
149193 service = self ._prefix + service
150194
151- http_headers = {
152- 'User-Agent' : self .user_agent or consts .USER_AGENT ,
153- 'Content-Type' : 'application/xml' ,
154- }
195+ http_headers = {}
155196
156197 if kwargs .get ('compress' , True ):
157198 http_headers ['Accept' ] = '*/*'
@@ -161,13 +202,10 @@ def call(self, service, method, *args, **kwargs):
161202 http_headers .update (kwargs .get ('raw_headers' ))
162203
163204 request = transports .Request ()
164- request .endpoint = self .endpoint_url
165205 request .service = service
166206 request .method = method
167207 request .args = args
168208 request .transport_headers = http_headers
169- request .timeout = self .timeout
170- request .proxy = self .proxy
171209 request .identifier = kwargs .get ('id' )
172210 request .mask = kwargs .get ('mask' )
173211 request .filter = kwargs .get ('filter' )
@@ -244,8 +282,7 @@ def iter_call(self, service, method, *args, **kwargs):
244282 break
245283
246284 def __repr__ (self ):
247- return "<Client: endpoint=%s, user=%r>" % (self .endpoint_url ,
248- self .auth )
285+ return "Client(transport=%r, auth=%r)" % (self .transport , self .auth )
249286
250287 __str__ = __repr__
251288
0 commit comments