(*) Peer has new fields person_ids and site_ids
[plcapi.git] / PLC / Methods / RefreshPeer.py
1 #
2 # Thierry Parmentelat - INRIA
3
4
5 import xmlrpclib
6
7 from PLC.Faults import *
8 from PLC.Method import Method
9 from PLC.Parameter import Parameter, Mixed
10 from PLC.Auth import Auth
11
12 from PLC.Peers import Peer, Peers
13 from PLC.Persons import Person, Persons
14
15 from PLC.Cache import Cache
16
17 class RefreshPeer(Method):
18     """
19     First queries a remote PLC for its name and updates the local peers table
20
21     Then proceeds with fetching objects on the remote PLC, and updates the
22     local database accordingly
23
24     It requires the remote peer to be aware of our own name (as configured in PLC_NAME)
25
26     Returns a dict containing
27     (*) 'peername' :   the peer's name
28     (*) 'new_xxx':     the number of new objects from that peer - may be negative
29     (*) 'timers':      various stats on performance for optimization
30
31     """
32     
33     roles = ['admin']
34     
35     accepts = [ Auth(),
36                 Mixed(Peer.fields['peer_id'],
37                       Peer.fields['peername']),
38                 ]
39     
40     returns = Parameter(dict, 
41                         'new_sites '
42                         'new_keys '
43                         'new_nodes '
44                         'new_persons '
45                         'new_slice_attribute_types '
46                         'new_slices '
47                         'new_slice_attributes '
48                         'timers ')
49
50     def call (self, auth, peer_id_or_peername):
51         
52         ### retrieve peer info
53         peers = Peers (self.api,[peer_id_or_peername])
54         try:
55             peer=peers[0]
56         except:
57             raise PLCInvalidArgument,'RefreshPeer: no such peer:%r'%peer_id_or_peername
58         
59         ### retrieve account info
60         auth_person_id = peer['auth_person_id']
61         persons = Persons (self.api,[auth_person_id])
62         try:
63             person = persons[0]
64         except:
65             raise PLCInvalidArgument,'RefreshPeer: no such person_id:%d'%auth_person_id
66         
67         ## connect to the peer's API
68         url=peer['peer_url']
69         apiserver = xmlrpclib.ServerProxy (url,allow_none=True)
70
71         ### build up foreign auth
72         auth={ 'Username': person['email'],
73                'AuthMethod' : 'password',
74                'AuthString' : person['password'],
75                'Role' : 'admin' ,
76                }
77
78         # xxx
79         # right now we *need* the remote peer to know our name
80         # (this is used in the GetPeerData that we issue)
81         # in general this will be true
82         # however if anyone decides to change its own plc name things can get wrong
83         # doing this should ensure things become right again after some iterations
84         # that is, hopefully
85         # might wish to change this policy once we have peer authentication, maybe
86         
87         # make sure we have the right name for that peer
88         peername = apiserver.GetPeerName (auth)
89         peer.update_name(peername)
90
91         # we need a peer_id from there on
92         peer_id = peer['peer_id']
93
94         print 'Got peer_id',peer_id
95
96         cache = Cache (self.api, peer_id, apiserver, auth)
97         result = cache.refresh_peer ()
98         result['peername']=peername
99
100         return result