10 except (socket.error, IOError, OSError):
17 _expected_methods = set(
18 ['AddNodeTag', 'AddConfFile', 'DeletePersonTag', 'AddNodeType', 'DeleteBootState', 'SliceListNames', 'DeleteKey',
19 'SliceGetTicket', 'SliceUsersList', 'SliceUpdate', 'GetNodeGroups', 'SliceCreate', 'GetNetworkMethods', 'GetNodeFlavour',
20 'DeleteNode', 'BootNotifyOwners', 'AddPersonKey', 'AddNode', 'UpdateNodeGroup', 'GetAddressTypes', 'AddIlink', 'DeleteNetworkType',
21 'GetInitScripts', 'GenerateNodeConfFile', 'AddSite', 'BindObjectToPeer', 'SliceListUserSlices', 'GetPeers', 'AddPeer', 'DeletePeer',
22 'AddRole', 'DeleteRole', 'SetPersonPrimarySite', 'AddSiteAddress', 'SliceDelete', 'NotifyPersons', 'GetKeyTypes', 'GetConfFiles',
23 'GetIlinks', 'AddTagType', 'GetNodes', 'DeleteNodeTag', 'DeleteSliceFromNodesWhitelist', 'UpdateAddress', 'ResetPassword',
24 'AddSliceToNodesWhitelist', 'AddRoleToTagType', 'AddLeases', 'GetAddresses', 'AddInitScript', 'RebootNode', 'GetPCUTypes',
25 'RefreshPeer', 'GetBootMedium', 'UpdateKey', 'UpdatePCU', 'GetSession', 'AddInterfaceTag', 'UpdatePCUType', 'GetInterfaces',
26 'SliceExtendedInfo', 'SliceNodesList', 'DeleteRoleFromTagType', 'DeleteSlice', 'GetSites', 'DeleteMessage', 'GetSliceFamily',
27 'GetPlcRelease', 'UpdateTagType', 'AddSliceInstantiation', 'ResolveSlices', 'GetSlices', 'DeleteRoleFromPerson', 'GetSessions',
28 'UpdatePeer', 'VerifyPerson', 'GetPersonTags', 'DeleteKeyType', 'AddSlice', 'SliceUserAdd', 'DeleteSession', 'GetMessages',
29 'DeletePCU', 'GetPeerData', 'DeletePersonFromSite', 'DeleteTagType', 'GetPCUs', 'UpdateLeases', 'AddMessage',
30 'DeletePCUProtocolType', 'DeleteInterfaceTag', 'AddPersonToSite', 'GetSlivers', 'SliceNodesDel', 'DeleteAddressTypeFromAddress',
31 'AddNodeGroup', 'GetSliceTags', 'DeleteSite', 'GetSiteTags', 'UpdateMessage', 'DeleteSliceFromNodes', 'SliceRenew',
32 'UpdatePCUProtocolType', 'DeleteSiteTag', 'GetPCUProtocolTypes', 'GetEvents', 'GetSliceTicket', 'AddPersonTag', 'BootGetNodeDetails',
33 'DeleteInterface', 'DeleteNodeGroup', 'AddPCUProtocolType', 'BootCheckAuthentication', 'AddSiteTag', 'AddAddressTypeToAddress',
34 'DeleteConfFile', 'DeleteInitScript', 'DeletePerson', 'DeleteIlink', 'DeleteAddressType', 'AddBootState', 'AuthCheck',
35 'NotifySupport', 'GetSliceInstantiations', 'AddPCUType', 'AddPCU', 'AddSession', 'GetEventObjects', 'UpdateSiteTag',
36 'UpdateNodeTag', 'AddPerson', 'BlacklistKey', 'UpdateInitScript', 'AddSliceToNodes', 'RebootNodeWithPCU', 'GetNodeTags',
37 'GetSliceKeys', 'GetSliceSshKeys', 'AddNetworkMethod', 'SliceNodesAdd', 'DeletePersonFromSlice', 'ReportRunlevel',
38 'GetNetworkTypes', 'UpdateSite', 'DeleteConfFileFromNodeGroup', 'UpdateNode', 'DeleteSliceInstantiation', 'DeleteSliceTag',
39 'BootUpdateNode', 'UpdatePerson', 'UpdateConfFile', 'SliceUserDel', 'DeleteLeases', 'AddConfFileToNodeGroup', 'UpdatePersonTag',
40 'DeleteConfFileFromNode', 'AddPersonToSlice', 'UnBindObjectFromPeer', 'AddNodeToPCU', 'GetLeaseGranularity', 'DeletePCUType',
41 'GetTagTypes', 'GetNodeTypes', 'UpdateInterfaceTag', 'GetRoles', 'UpdateSlice', 'UpdateSliceTag', 'AddSliceTag', 'AddNetworkType',
42 'AddInterface', 'AddAddressType', 'AddRoleToPerson', 'DeleteNodeType', 'GetLeases', 'UpdateInterface', 'SliceInfo', 'DeleteAddress',
43 'SliceTicketGet', 'GetPersons', 'GetWhitelist', 'AddKeyType', 'UpdateAddressType', 'GetPeerName', 'DeleteNetworkMethod',
44 'UpdateIlink', 'AddConfFileToNode', 'GetKeys', 'DeleteNodeFromPCU', 'GetInterfaceTags', 'GetBootStates', 'SetInterfaceSens', 'SetNodeLoadm',
45 'GetInterfaceRate', 'GetNodeLoadw', 'SetInterfaceKey', 'GetNodeSlices', 'GetNodeLoadm', 'SetSliceVref', 'GetInterfaceIwpriv', 'SetNodeLoadw',
46 'SetNodeSerial', 'GetNodePlainBootstrapfs', 'SetNodeMEMw', 'GetNodeResponse', 'SetInterfaceRate', 'SetSliceInitscript',
47 'SetNodeFcdistro', 'GetNodeLoady', 'SetNodeArch', 'SetNodeKargs', 'SetNodeMEMm', 'SetNodeBWy', 'SetNodeBWw',
48 'SetInterfaceSecurityMode', 'SetNodeBWm', 'SetNodeASType', 'GetNodeKargs', 'GetPersonColumnconf', 'GetNodeResponsem',
49 'GetNodeCPUy', 'GetNodeCramfs', 'SetNodeSlicesw', 'SetPersonColumnconf', 'SetNodeSlicesy', 'GetNodeCPUw', 'GetNodeBWy',
50 'GetNodeCPUm', 'GetInterfaceDriver', 'GetNodeLoad', 'GetInterfaceMode', 'GetNodeSerial', 'SetNodeSlicesm', 'SetNodeLoady',
51 'GetNodeReliabilityw', 'SetSliceFcdistro', 'GetNodeReliabilityy', 'SetInterfaceEssid', 'SetSliceInitscriptCode',
52 'GetNodeExtensions', 'GetSliceOmfControl', 'SetNodeCity', 'SetInterfaceIfname', 'SetNodeHrn', 'SetNodeNoHangcheck',
53 'GetNodeNoHangcheck', 'GetSliceFcdistro', 'SetNodeCountry', 'SetNodeKvariant', 'GetNodeKvariant', 'GetNodeMEMy',
54 'SetInterfaceIwpriv', 'GetNodeMEMw', 'SetInterfaceBackdoor', 'GetInterfaceFreq', 'SetInterfaceChannel', 'SetInterfaceNw',
55 'GetPersonShowconf', 'GetSliceInitscriptCode', 'SetNodeMEM', 'GetInterfaceEssid', 'GetNodeMEMm', 'SetInterfaceMode',
56 'SetInterfaceIwconfig', 'GetNodeSlicesm', 'GetNodeBWm', 'SetNodePlainBootstrapfs', 'SetNodeRegion', 'SetNodeCPU',
57 'GetNodeSlicesw', 'SetNodeBW', 'SetNodeSlices', 'SetNodeCramfs', 'GetNodeSlicesy', 'GetInterfaceKey', 'GetSliceInitscript',
58 'SetNodeCPUm', 'SetSliceArch', 'SetNodeLoad', 'SetNodeResponse', 'GetSliceSliverHMAC', 'GetNodeBWw', 'GetNodeRegion',
59 'SetNodeMEMy', 'GetNodeASType', 'SetNodePldistro', 'GetSliceArch', 'GetNodeCountry', 'SetSliceOmfControl', 'GetNodeHrn',
60 'GetNodeCity', 'SetInterfaceAlias', 'GetNodeBW', 'GetNodePldistro', 'GetSlicePldistro', 'SetNodeASNumber', 'GetSliceHmac',
61 'SetSliceHmac', 'GetNodeMEM', 'GetNodeASNumber', 'GetInterfaceAlias', 'GetSliceVref', 'GetNodeArch', 'GetSliceSshKey',
62 'GetInterfaceKey4', 'GetInterfaceKey2', 'GetInterfaceKey3', 'GetInterfaceKey1', 'GetInterfaceBackdoor', 'GetInterfaceIfname',
63 'SetSliceSliverHMAC', 'SetNodeReliability', 'GetNodeCPU', 'SetPersonShowconf', 'SetNodeExtensions', 'SetNodeCPUy',
64 'SetNodeCPUw', 'GetNodeResponsew', 'SetNodeResponsey', 'GetInterfaceSens', 'SetNodeResponsew', 'GetNodeResponsey',
65 'GetNodeReliability', 'GetNodeReliabilitym', 'SetNodeResponsem', 'SetInterfaceDriver', 'GetInterfaceSecurityMode',
66 'SetNodeDeployment', 'SetNodeReliabilitym', 'GetNodeFcdistro', 'SetInterfaceFreq', 'GetInterfaceNw', 'SetNodeReliabilityy',
67 'SetNodeReliabilityw', 'GetInterfaceIwconfig', 'SetSlicePldistro', 'SetSliceSshKey', 'GetNodeDeployment', 'GetInterfaceChannel',
68 'SetInterfaceKey2', 'SetInterfaceKey3', 'SetInterfaceKey1', 'SetInterfaceKey4'])
70 _required_methods = set()
72 def __init__(self, username=None, password=None, sessionkey=None,
73 hostname = "www.planet-lab.eu",
74 urlpattern = "https://%(hostname)s:443/PLCAPI/",
75 localPeerName = "PLE"):
76 if sessionkey is not None:
77 self.auth = dict(AuthMethod='session', session=sessionkey)
78 elif username is not None and password is not None:
79 self.auth = dict(AuthMethod='password', Username=username, AuthString=password)
81 self.auth = dict(AuthMethod='anonymous')
83 self._localPeerName = localPeerName
85 self.api = xmlrpclib.ServerProxy(
86 urlpattern % {'hostname':hostname},
92 # validate XMLRPC server checking supported API calls
93 methods = set(_retry(self.api.system.listMethods)())
94 if self._required_methods - methods:
95 warnings.warn("Unsupported REQUIRED methods: %s" % ( ", ".join(sorted(self._required_methods - methods)), ) )
97 if self._expected_methods - methods:
98 warnings.warn("Unsupported EXPECTED methods: %s" % ( ", ".join(sorted(self._expected_methods - methods)), ) )
102 network_types = _retry(self.api.GetNetworkTypes)(self.auth)
103 except (xmlrpclib.ProtocolError, xmlrpclib.Fault),e:
104 warnings.warn(str(e))
110 def network_types(self):
112 return self._network_types
113 except AttributeError:
114 self._network_types = _retry(self.api.GetNetworkTypes)(self.auth)
115 return self._network_types
120 return self._peer_map
121 except AttributeError:
122 peers = _retry(self.api.GetPeers)(self.auth, {}, ['shortname','peername','peer_id'])
123 self._peer_map = dict(
124 (peer['shortname'], peer['peer_id'])
127 self._peer_map.update(
128 (peer['peername'], peer['peer_id'])
131 self._peer_map.update(
132 (peer['peer_id'], peer['shortname'])
135 self._peer_map[None] = self._localPeerName
136 return self._peer_map
139 def GetNodeFlavour(self, node):
141 Returns detailed information on a given node's flavour, i.e. its base installation.
143 This depends on the global PLC settings in the PLC_FLAVOUR area, optionnally overridden by any of the following tags if set on that node:
144 'arch', 'pldistro', 'fcdistro', 'deployment', 'extensions'
148 * node : int or string
149 - int, Node identifier
150 - string, Fully qualified hostname
155 * extensions : array of string, extensions to add to the base install
156 * fcdistro : string, the fcdistro this node should be based upon
157 * nodefamily : string, the nodefamily this node should be based upon
158 * plain : boolean, use plain bootstrapfs image if set (for tests)
160 if not isinstance(node, (str, int, long)):
161 raise ValueError, "Node must be either a non-unicode string or an int"
162 return _retry(self.api.GetNodeFlavour)(self.auth, node)
164 def GetNodes(self, nodeIdOrName=None, fields=None, **kw):
166 Returns an array of structs containing details about nodes.
167 If nodeIdOrName is specified and is an array of node identifiers or hostnames,
168 or the filters keyword argument with struct of node attributes,
169 or node attributes by keyword argument,
170 only nodes matching the filter will be returned.
172 If fields is specified, only the specified details will be returned.
173 NOTE that if fields is unspecified, the complete set of native fields are returned,
174 which DOES NOT include tags at this time.
176 Some fields may only be viewed by admins.
180 fields: an optional list of fields to retrieve. The default is all.
182 filters: an optional mapping with custom filters, which is the only
183 way to support complex filters like negation and numeric comparisons.
185 peer: a string (or sequence of strings) with the name(s) of peers
186 to filter - or None for local nodes.
188 if fields is not None:
189 fieldstuple = (fields,)
192 if nodeIdOrName is not None:
193 return _retry(self.api.GetNodes)(self.auth, nodeIdOrName, *fieldstuple)
195 filters = kw.pop('filters',{})
198 peer = kw.pop('peer')
200 nameToId = self.peer_map.get
202 if hasattr(peer, '__iter__'):
203 # we can't mix local and external nodes, so
204 # split and re-issue recursively in that case
205 if None in peer or self._localPeerName in peer:
208 if self._localPeerName in peer:
209 peer.remove(self._localPeerName)
211 self.GetNodes(nodeIdOrName, fields, filters=filters, peer=peer, **kw)
212 + self.GetNodes(nodeIdOrName, fields, filters=filters, peer=None, **kw)
215 peer_filter = map(nameToId, peer)
216 elif peer is None or peer == self._localPeerName:
219 peer_filter = nameToId(peer)
221 filters['peer_id'] = peer_filter
224 return _retry(self.api.GetNodes)(self.auth, filters, *fieldstuple)
226 def GetNodeTags(self, nodeTagId=None, fields=None, **kw):
227 if fields is not None:
228 fieldstuple = (fields,)
231 if nodeTagId is not None:
232 return _retry(self.api.GetNodeTags)(self.auth, nodeTagId, *fieldstuple)
234 filters = kw.pop('filters',{})
236 return _retry(self.api.GetNodeTags)(self.auth, filters, *fieldstuple)
238 def GetSliceTags(self, sliceTagId=None, fields=None, **kw):
239 if fields is not None:
240 fieldstuple = (fields,)
243 if sliceTagId is not None:
244 return _retry(self.api.GetSliceTags)(self.auth, sliceTagId, *fieldstuple)
246 filters = kw.pop('filters',{})
248 return _retry(self.api.GetSliceTags)(self.auth, filters, *fieldstuple)
251 def GetInterfaces(self, interfaceIdOrIp=None, fields=None, **kw):
252 if fields is not None:
253 fieldstuple = (fields,)
256 if interfaceIdOrIp is not None:
257 return _retry(self.api.GetInterfaces)(self.auth, interfaceIdOrIp, *fieldstuple)
259 filters = kw.pop('filters',{})
261 return _retry(self.api.GetInterfaces)(self.auth, filters, *fieldstuple)
263 def GetSlices(self, sliceIdOrName=None, fields=None, **kw):
264 if fields is not None:
265 fieldstuple = (fields,)
268 if sliceIdOrName is not None:
269 return _retry(self.api.GetSlices)(self.auth, sliceIdOrName, *fieldstuple)
271 filters = kw.pop('filters',{})
273 return _retry(self.api.GetSlices)(self.auth, filters, *fieldstuple)
275 def UpdateSlice(self, sliceIdOrName, **kw):
276 return _retry(self.api.UpdateSlice)(self.auth, sliceIdOrName, kw)