From 865c7ad3dba34691309904e49cb5885e8d9cd5a1 Mon Sep 17 00:00:00 2001 From: Thierry Parmentelat Date: Tue, 28 Nov 2006 14:55:00 +0000 Subject: [PATCH] (*) direct cross refs redefined as NOT NULL in the database (e.g. Node:site_id, Person:site_id, Slice:creator_person_id) NOTE. I screwed up, this was already in former commit of planetlab4.sql, (*) cross-ref mechanism reviewed could not handle several xrefs with the same type in the same table (*) undid ad-hoc trick for selecting local/foreign nodes (was named scope) had no added-value and was only used in TestPeers anyway --- PLC/Cache.py | 84 ++++++++++++++++++-------- PLC/Methods/GetNodes.py | 5 +- PLC/Nodes.py | 15 ++--- PLC/Persons.py | 17 ++---- PLC/Sites.py | 8 +-- PLC/SliceAttributeTypes.py | 2 +- PLC/Slices.py | 15 ++--- TestPeers.py | 118 +++++++++++++++++++++++-------------- peers-test.mk | 22 ++++--- planetlab4.sql | 28 ++++----- 10 files changed, 185 insertions(+), 129 deletions(-) diff --git a/PLC/Cache.py b/PLC/Cache.py index 5811357..61ebcfc 100644 --- a/PLC/Cache.py +++ b/PLC/Cache.py @@ -71,6 +71,7 @@ class Cache: return local_id + # for handling simple n-to-n relation tables, like e.g. slice_node class XrefTable: def __init__ (self, api, tablename, class1, class2): @@ -109,7 +110,7 @@ class Cache: # classname: the type of objects we are talking about; e.g. 'Slice' # peer_object_list list of objects at a given peer - e.g. peer.GetSlices() # alien_xref_objs_dict : a dict {'classname':alien_obj_list} e.g. {'Node':peer.GetNodes()} - # his must match the keys in xref_specs + # we need an entry for each class mentioned in the class's foreign_xrefs # lambda_ignore : the alien objects are ignored if this returns true def update_table (self, classname, @@ -118,6 +119,7 @@ class Cache: lambda_ignore=lambda x:False, report_name_conflicts = True): + verbose ("============================== entering update_table on",classname) peer_id=self.peer_id attrs = class_attributes (classname) @@ -130,11 +132,15 @@ class Cache: ## allocate transcoders and xreftables once, for each item in foreign_xrefs # create a dict 'classname' -> {'transcoder' : ..., 'xref_table' : ...} - accessories = dict( - [ (xref_classname, - {'transcoder':Cache.Transcoder (self.api,xref_classname,alien_xref_objs_dict[xref_classname]), - 'xref_table':Cache.XrefTable (self.api,xref_spec['table'],classname,xref_classname)}) - for xref_classname,xref_spec in foreign_xrefs.iteritems()]) + xref_accessories = dict( + [ (xref['field'], + {'transcoder' : Cache.Transcoder (self.api,xref['class'],alien_xref_objs_dict[xref['class']]), + 'xref_table' : Cache.XrefTable (self.api,xref['table'],classname,xref['class'])}) + for xref in foreign_xrefs ]) + + # the fields that are direct references, like e.g. site_id in Node + # determined lazily, we need an alien_object to do that, and we may have none here + direct_ref_fields = None ### get current local table # get ALL local objects so as to cope with @@ -175,10 +181,11 @@ class Cache: if local_object ['peer_id'] is None: if report_name_conflicts: ### xxx send e-mail - print '==================== We are in trouble here' - print 'The %s object named %s is natively defined twice'%(classname,object_name) - print 'Once on this PLC and once on peer %d'%peer_id + print '!!!!!!!!!! We are in trouble here' + print 'The %s object named %s is natively defined twice, '%(classname,object_name), + print 'once on this PLC and once on peer %d'%peer_id print 'We dont raise an exception so that the remaining updates can still take place' + print '!!!!!!!!!!' continue if local_object['peer_id'] != peer_id: ### the object has changed its plc, @@ -186,6 +193,9 @@ class Cache: ### we can assume the object just moved ### needs to update peer_id though local_object['peer_id'] = peer_id + # update all fields as per foreign_fields + for field in foreign_fields: + local_object[field]=alien_object[field] verbose ('update_table FOUND',object_name) except: ### create a new entry @@ -194,24 +204,44 @@ class Cache: # insert in index local_objects_index[class_key]=local_object verbose ('update_table CREATED',object_name) - - # go on with update - for field in foreign_fields: - local_object[field]=alien_object[field] + # update all fields as per foreign_fields + for field in foreign_fields: + local_object[field]=alien_object[field] + # this is tricky; at this point we may have primary_key unspecified, + # but we need it for handling xrefs below, so we'd like to sync to get one + # on the other hand some required fields may be still missing so + # the DB would refuse to sync in this case (e.g. site_id in Node) + # so let's fill them with 1 so we can sync, this will be overridden below + # lazily determine this set of fields now + if direct_ref_fields is None: + direct_ref_fields=[] + for xref in foreign_xrefs: + field=xref['field'] + verbose('checking field %s for direct_ref'%field) + if isinstance(alien_object[field],int): + direct_ref_fields.append(field) + verbose("FOUND DIRECT REFS",direct_ref_fields) + for field in direct_ref_fields: + local_object[field]=1 + verbose('Early sync on',local_object) + local_object.sync() + verbose('Early syncing of %s, reloading'%object_name) + # sigh: now we have to reload it because of side-effects, like e.g. on Slice.expires + local_object=table_class(self.api, {class_key:object_name})[0] + verbose('After reload',local_object) # this row is now valid local_object.uptodate=True new_count += 1 - local_object.sync() # manage cross-refs - for xref_classname,xref_spec in foreign_xrefs.iteritems(): - field=xref_spec['field'] - alien_xref_obj_list = alien_xref_objs_dict[xref_classname] + for xref in foreign_xrefs: + field=xref['field'] + alien_xref_obj_list = alien_xref_objs_dict[xref['class']] alien_value = alien_object[field] - transcoder = accessories[xref_classname]['transcoder'] + transcoder = xref_accessories[xref['field']]['transcoder'] if isinstance (alien_value,list): - verbose ('update_table list-transcoding ',xref_classname,' aliens=',alien_value,) + verbose ('update_table list-transcoding ',xref['class'],' aliens=',alien_value,) local_values=[] for a in alien_value: try: @@ -220,20 +250,24 @@ class Cache: # could not transcode - might be from another peer that we dont know about.. pass verbose (" transcoded as ",local_values) - xref_table = accessories[xref_classname]['xref_table'] - # newly created objects dont have xrefs yet + xref_table = xref_accessories[xref['field']]['xref_table'] + # newly created objects dont have xref fields set yet try: - former_xrefs=local_object[xref_spec['field']] + former_xrefs=local_object[xref['field']] except: former_xrefs=[] xref_table.update_item (local_object[primary_key], former_xrefs, local_values) elif isinstance (alien_value,int): - verbose ('update_table atom-transcoding ',xref_classname,' aliens=',alien_value,) + verbose ('update_table atom-transcoding ',xref['class'],' aliens=',alien_value,) new_value = transcoder.transcode(alien_value) local_object[field] = new_value - local_object.sync() + + ### this object is completely updated, let's save it + verbose('FINAL sync on %s:'%object_name,local_object) + local_object.sync() + ### delete entries that are not uptodate for local_object in local_objects: @@ -396,7 +430,7 @@ class Cache: return slice['creator_person_id'] == 1 nb_new_slices = self.update_table ('Slice', plocal_slices, - {'Node': all_nodes, 'Person': all_persons}, + {'Node': all_nodes, 'Person': all_persons, 'Site': all_sites}, is_system_slice) # refresh slice attributes diff --git a/PLC/Methods/GetNodes.py b/PLC/Methods/GetNodes.py index 937b948..6206a7a 100644 --- a/PLC/Methods/GetNodes.py +++ b/PLC/Methods/GetNodes.py @@ -24,14 +24,13 @@ class GetNodes(Method): Node.fields['hostname'])], Filter(Node.fields)), Parameter([str], "List of fields to return", nullok = True), - Parameter(str,"scope string, can be either 'all', 'local' or 'foreign'"), ] returns = [Node.fields] - def call(self, auth, node_filter = None, return_fields = None, scope = 'all'): + def call(self, auth, node_filter = None, return_fields = None): # Get node information - nodes = Nodes(self.api, node_filter, return_fields, scope) + nodes = Nodes(self.api, node_filter, return_fields) # Remove admin only fields if 'admin' not in self.caller['roles']: diff --git a/PLC/Nodes.py b/PLC/Nodes.py index c8f0db7..f83c740 100644 --- a/PLC/Nodes.py +++ b/PLC/Nodes.py @@ -4,7 +4,7 @@ # Mark Huang # Copyright (C) 2006 The Trustees of Princeton University # -# $Id: Nodes.py,v 1.24 2006/11/25 09:35:36 thierry Exp $ +# $Id: Nodes.py,v 1.25 2006/11/28 10:25:03 thierry Exp $ # from types import StringTypes @@ -65,10 +65,10 @@ class Node(Row): # for Cache class_key = 'hostname' foreign_fields = ['boot_state','model','version','date_created','last_updated'] - foreign_xrefs = { + foreign_xrefs = [ # in this case, we dont need the 'table' but Cache will look it up, so... - 'Site' : { 'field' : 'site_id' , 'table' : 'unused' } , - } + {'field' : 'site_id' , 'class' : 'Site' , 'table' : 'unused-on-direct-refs' } , + ] def validate_hostname(self, hostname): if not valid_hostname(hostname): @@ -111,7 +111,7 @@ class Nodes(Table): database. """ - def __init__(self, api, node_filter = None, columns = None, scope = 'all'): + def __init__(self, api, node_filter = None, columns = None): Table.__init__(self, api, Node, columns) sql = "SELECT %s FROM view_nodes WHERE deleted IS False" % \ @@ -128,10 +128,5 @@ class Nodes(Table): node_filter = Filter(Node.fields, node_filter) sql += " AND (%s)" % node_filter.sql(api, "AND") - if scope == 'local': - sql += " AND (peer_id is NULL) " - elif scope == 'foreign': - sql += " AND (peer_id is NOT NULL) " - self.selectall(sql) diff --git a/PLC/Persons.py b/PLC/Persons.py index 822a27f..87e936f 100644 --- a/PLC/Persons.py +++ b/PLC/Persons.py @@ -4,7 +4,7 @@ # Mark Huang # Copyright (C) 2006 The Trustees of Princeton University # -# $Id: Persons.py,v 1.20 2006/11/24 12:06:00 thierry Exp $ +# $Id: Persons.py,v 1.21 2006/11/25 09:35:36 thierry Exp $ # from types import StringTypes @@ -57,17 +57,12 @@ class Person(Row): class_key = 'email' foreign_fields = ['first_name', 'last_name', 'title', 'email', 'phone', 'url', 'bio', 'enabled', 'password', 'last_updated', 'date_created'] - #foreign_xrefs = { 'Node' : { 'field' : 'node_ids' , - # 'table': 'slice_node' } } - foreign_xrefs = { - 'Key' : { 'field' : 'key_ids', 'table' : 'person_key' } , - 'Site' : { 'field' : 'site_ids', 'table' : 'person_site'}, -# 'key_ids': Parameter([int], "List of key identifiers"), + foreign_xrefs = [ + {'field' : 'key_ids', 'class': 'Key', 'table' : 'person_key' } , + {'field' : 'site_ids', 'class': 'Site', 'table' : 'person_site'}, +# xxx this is not handled by Cache yet # 'role_ids': Parameter([int], "List of role identifiers"), -# 'roles': Parameter([str], "List of roles"), -# 'site_ids': Parameter([int], "List of site identifiers"), -# 'slice_ids': Parameter([int], "List of slice identifiers"), -} +] def validate_email(self, email): """ diff --git a/PLC/Sites.py b/PLC/Sites.py index 84afa16..14cd51e 100644 --- a/PLC/Sites.py +++ b/PLC/Sites.py @@ -48,13 +48,7 @@ class Site(Row): foreign_fields = ['abbreviated_name', 'name', 'is_public', 'latitude', 'longitude', 'url', 'date_created', 'last_updated', 'max_slices', 'max_slivers', ] - foreign_xrefs = { -#'person_ids', -#'slice_ids', -#'node_ids', -#'address_ids', -#'pcu_ids', -} + foreign_xrefs = {} def validate_name(self, name): if not len(name): diff --git a/PLC/SliceAttributeTypes.py b/PLC/SliceAttributeTypes.py index f3817ef..65ec0fa 100644 --- a/PLC/SliceAttributeTypes.py +++ b/PLC/SliceAttributeTypes.py @@ -26,7 +26,7 @@ class SliceAttributeType(Row): # for Cache class_key = 'name' foreign_fields = ['description','min_role_id'] - foreign_xrefs = {} + foreign_xrefs = [] def validate_name(self, name): if not len(name): diff --git a/PLC/Slices.py b/PLC/Slices.py index 234526f..e8f64cc 100644 --- a/PLC/Slices.py +++ b/PLC/Slices.py @@ -24,7 +24,6 @@ class Slice(Row): fields = { 'slice_id': Parameter(int, "Slice identifier"), 'site_id': Parameter(int, "Identifier of the site to which this slice belongs"), - 'peer_id': Parameter(int, "Peer at which this slice was created", nullok = True), 'name': Parameter(str, "Slice name", max = 32), 'instantiation': Parameter(str, "Slice instantiation state"), 'url': Parameter(str, "URL further describing this slice", max = 254, nullok = True), @@ -36,15 +35,17 @@ class Slice(Row): 'node_ids': Parameter([int], "List of nodes in this slice", ro = True), 'person_ids': Parameter([int], "List of accounts that can use this slice", ro = True), 'slice_attribute_ids': Parameter([int], "List of slice attributes", ro = True), + 'peer_id': Parameter(int, "Peer at which this slice was created", nullok = True), } # for Cache class_key = 'name' - foreign_fields = ['instantiation', 'url', 'description', - 'max_nodes', 'created', 'expires'] - foreign_xrefs = { - 'Node' : { 'field' : 'node_ids' , 'table': 'slice_node' }, - 'Person' : { 'field': 'person_ids', 'table' : 'slice_person'}, - } + foreign_fields = ['instantiation', 'url', 'description', 'max_nodes', 'created', 'expires'] + foreign_xrefs = [ + {'field': 'node_ids' , 'class': 'Node', 'table': 'slice_node' }, + {'field': 'person_ids', 'class': 'Person', 'table': 'slice_person'}, + {'field': 'creator_person_id', 'class': 'Person', 'table': 'unused-on-direct-refs'}, + {'field': 'site_id', 'class': 'Site', 'table': 'unused-on-direct-refs'}, + ] def validate_name(self, name): # N.B.: Responsibility of the caller to ensure that login_base diff --git a/TestPeers.py b/TestPeers.py index a9083ec..d7220bb 100755 --- a/TestPeers.py +++ b/TestPeers.py @@ -84,19 +84,31 @@ def define_test (sites,keys,persons,nodes,slices,fast_mode): fast_flag=fast_mode def show_test(): - print '%d sites, %d keys, %d persons, %d nodes & %d slices'%(number_sites, number_keys,number_persons, - number_nodes,number_slices) + print '%d sites, %d keys, %d persons, %d nodes & %d slices'%( + number_sites, number_keys,number_persons,number_nodes,number_slices) -def fast(): +def mini(): define_test(1,1,1,1,1,True) def normal(): define_test (sites=4,keys=2,persons=4,nodes=5,slices=4,fast_mode=False) +big_factor=4 def big(): - define_test (sites=16,keys=8,persons=16,nodes=20,slices=16,fast_mode=False) + global number_sites, number_keys, number_persons, number_nodes, number_slices + normal() + (number_sites,number_keys,number_persons,number_nodes,number_slices) = [ + big_factor * x for x in (number_sites,number_keys,number_persons,number_nodes,number_slices)] + +huge_factor=50 +def huge(): + global number_sites, number_keys, number_persons, number_nodes, number_slices + normal() + (number_sites,number_keys,number_persons,number_nodes,number_slices) = [ + huge_factor * x for x in (number_sites,number_keys,number_persons,number_nodes,number_slices)] -fast() +# use fast by default in interactive mode +mini() #normal() #################### @@ -500,13 +512,13 @@ def test02_person_n_ks (np,nks,add_if_true,args=[1,2]): #################### # retrieves node_id from hostname - checks for local nodes only def get_local_node_id(i,nodename): - return s[i].GetNodes(a[i],[nodename],None,'local')[0]['node_id'] + return s[i].GetNodes(a[i],{'hostname':nodename,'peer_id':None})[0]['node_id'] # clean all local nodes - foreign nodes are not supposed to be cleaned up manually def clean_all_nodes (args=[1,2]): for i in args: print '%02d:== Cleaning all nodes'%i - loc_nodes = s[i].GetNodes(a[i],None,None,'local') + loc_nodes = s[i].GetNodes(a[i],{'peer_id':None}) for node in loc_nodes: print '%02d:==== Cleaning node %d'%(i,node['node_id']) s[i].DeleteNode(a[i],node['node_id']) @@ -662,62 +674,64 @@ def test05_sa (args=[1,2]): # readable dumps ############################## def p_site (s): - print (s['site_id'],s['peer_id'],s['login_base'],s['name'],s['node_ids']) + print s['site_id'],s['peer_id'],s['login_base'],s['name'],s['node_ids'] def p_key (k): - print (k['key_id'],k['peer_id'],k['key']) + print k['key_id'],k['peer_id'],k['key'] def p_person (p): - print (p['person_id'],p['peer_id'],p['email'],'keys:',p['key_ids'],'sites:',p['site_ids']) + print p['person_id'],p['peer_id'],p['email'],'keys:',p['key_ids'],'sites:',p['site_ids'] def p_node(n): - print (n['node_id'],n['peer_id'],n['hostname'],'sls=',n['slice_ids'],'site=',n['site_id']) + print n['node_id'],n['peer_id'],n['hostname'],'sls=',n['slice_ids'],'site=',n['site_id'] def p_slice(s): - print (s['slice_id'],s['peer_id'],s['name'],'nodes=',s['node_ids'],'persons=',s['person_ids']) - print '---',('sas=',s['slice_attribute_ids'],s['name'],'crp=',s['creator_person_id']) + print s['slice_id'],s['peer_id'],s['name'],'nodes=',s['node_ids'],'persons=',s['person_ids'] + print '---','sas=',s['slice_attribute_ids'],s['name'],'crp=',s['creator_person_id'],'e=',s['expires'] def p_sat(sat): - print (sat['attribute_type_id'],sat['peer_id'], sat['name'], sat['min_role_id'], sat['description']) + print sat['attribute_type_id'],sat['peer_id'], sat['name'], sat['min_role_id'], sat['description'] def p_sa (sa): - print (sa['slice_attribute_id'],sa['peer_id'],sa['name'],'AT_id:',sa['attribute_type_id']) - print '---',('v=',sa['value'],'sl=',sa['slice_id'],'n=',sa['node_id']) - -def p_sliver (x): - print ('SLIVERS for : hostname',x['hostname']) - print ('%d config files'%len(x['conf_files'])) - for sv in x['slivers']: - p_sliver_slice(sv,x['hostname']) + print sa['slice_attribute_id'],sa['peer_id'],sa['name'],'AT_id:',sa['attribute_type_id'] + print '---','v=',sa['value'],'sl=',sa['slice_id'],'n=',sa['node_id'] import pprint pretty_printer=pprint.PrettyPrinter(5) -def p_sliver_slice(sliver,hostname): - print 'SLIVER on hostname %s, s='%hostname,sliver['name'] - print 'KEYS', +def p_sliver (margin,x): + print margin,'SLIVERS for : hostname',x['hostname'] + print margin,'%d config files'%len(x['conf_files']) + for sv in x['slivers']: + p_sliver_slice(margin,sv,x['hostname']) + +def p_sliver_slice(margin,sliver,hostname): + print margin,'SLIVER on hostname %s, s='%hostname,sliver['name'] + print margin,'KEYS', pretty_printer.pprint(sliver['keys']) - print 'ATTRIBUTES', + print margin,'ATTRIBUTES', pretty_printer.pprint(sliver['attributes']) def dump (args=[1,2]): for i in args: - print 'SITES' + print '%02d:============================== DUMPING'%i + print '%02d: SITES'%i [p_site(x) for x in s[i].GetSites(a[i])] - print 'KEYS' + print '%02d: KEYS'%i [p_key(x) for x in s[i].GetKeys(a[i])] - print 'PERSONS' + print '%02d: PERSONS'%i [p_person(x) for x in s[i].GetPersons(a[i])] - print 'NODES' + print '%02d: NODES'%i [p_node(x) for x in s[i].GetNodes(a[i])] - print 'SLICES' + print '%02d: SLICES'%i [p_slice(x) for x in s[i].GetSlices(a[i])] - print 'Slice Attribute Types' + print '%02d: Slice Attribute Types'%i [p_sat(x) for x in s[i].GetSliceAttributeTypes(a[i])] - print 'Slice Attributes' + print '%02d: Slice Attributes'%i [p_sa(x) for x in s[i].GetSliceAttributes(a[i])] - print 'SLIVERS' - [p_sliver(x) for x in s[i].GetSlivers(a[i])] + print '%02d: SLIVERS'%i + [p_sliver('%02d:'%i,x) for x in s[i].GetSlivers(a[i])] + print '%02d:============================== END DUMP'%i ## for usage under the api @@ -751,7 +765,7 @@ def psa(): def pv (): for s in GetSlivers(): - p_sliver(s) + p_sliver('',s) def all(): print 'SITES' @@ -940,19 +954,32 @@ def test_all (): ### ad hoc test sequences def populate (): + timer_start() test_all_init() + timer_show() test01_site() + timer_show() test02_person() + timer_show() test03_node() + timer_show() test04_slice([1]) + timer_show() test04_slice_add_lnode([1]) + timer_show() test05_sat() + timer_show() test05_sa([1]) + timer_show() test00_refresh ("populate: refreshing peer 1",[1]) + timer_show() test04_slice_add_fnode([1]) + timer_show() test00_refresh("populate: refresh all") dump() + timer_show() +# temporary - scratch as needed def test_now (): test_all_init() test_all_sites () @@ -963,30 +990,33 @@ def test_now (): ##### def usage (): print "Usage: %s [-n] [-f]"%sys.argv[0] - print " -f runs faster (1 node - 1 slice)" - print " -b performs big run (4 times as large as normal)" print " -n runs test_now instead of test_all" print " -p runs populate instead of test_all" + print " -m run in mini mode (1 instance of each class)" + print " -b performs big run (%d times as large as normal)"%big_factor + print " -H performs huge run (%d times as large as normal)"%huge_factor sys.exit(1) def main (): try: - (o,a) = getopt.getopt(sys.argv[1:], "fnpb") + (o,a) = getopt.getopt(sys.argv[1:], "mnpbH") except: usage() func = test_all for (opt,val) in o: - if opt=='-f': - fast() - elif opt=='-b': - big() - elif opt=='-n': + if opt=='-n': print 'Running test_now' func = test_now elif opt=='-p': print 'Running populate' func = populate + elif opt=='-m': + mini() + elif opt=='-b': + big() + elif opt=='-H': + huge() else: usage() if a: diff --git a/peers-test.mk b/peers-test.mk index 8dc1687..9e9458f 100644 --- a/peers-test.mk +++ b/peers-test.mk @@ -24,16 +24,14 @@ pclean: papi1: rsync -a -v -C ./ root@$(PLC1):new_plc_api/ pplc1: - rsync -a -v -C ./PLC/ root@$(PLC1):$(CHROOT)$(APIDIR)/PLC/ - rsync -a -v -C ./planetlab4.sql root@$(PLC1):$(CHROOT)$(APIDIR)/planetlab4.sql + rsync -a -v -C ./planetlab4.sql ./PLC root@$(PLC1):$(CHROOT)$(APIDIR)/ papi2: rsync -a -v -C ./ root@$(PLC2):new_plc_api/ pplc2: - rsync -a -v -C ./PLC/ root@$(PLC2):$(CHROOT)$(APIDIR)/PLC/ - rsync -a -v -C ./planetlab4.sql root@$(PLC2):$(CHROOT)$(APIDIR)/planetlab4.sql + rsync -a -v -C ./planetlab4.sql ./PLC root@$(PLC2):$(CHROOT)$(APIDIR)/ #################### -DB=install-schema stop-clients clean-db restart +DB=install-schema stop-clients clean-db restart-db WEB=install-api restart db: $(DB) @@ -64,6 +62,11 @@ clean-db: @echo 'dropping db' @chroot $(CHROOT) psql -U postgres --port $(PORT) template1 -c 'drop database planetlab4' +restart-db: + @echo 'restarting db' + @chroot $(CHROOT) service plc stop db postgresql httpd + @chroot $(CHROOT) service plc start httpd postgresql db + restart: @echo 'Restarting PLC' @chroot $(CHROOT) service plc restart @@ -127,12 +130,17 @@ checkpoint: cp TestPeers.out TestPeers.ref cp TestPeers.out.nor TestPeers.ref.nor -frun: - python -u ./TestPeers.py -f > TestPeers.fout 2>&1 +mrun: + python -u ./TestPeers.py -m > TestPeers.mout 2>&1 brun: python -u ./TestPeers.py -b > TestPeers.bout 2>&1 prun: python -u ./TestPeers.py -p > TestPeers.pout 2>&1 +pbrun: + python -u ./TestPeers.py -p -b > TestPeers.pbout 2>&1 +phrun: + python -u ./TestPeers.py -p -H > TestPeers.phout 2>&1 + ####### HELP=rpm db-dump http diff --git a/planetlab4.sql b/planetlab4.sql index 6278b0d..4448c48 100644 --- a/planetlab4.sql +++ b/planetlab4.sql @@ -9,7 +9,7 @@ -- -- Copyright (C) 2006 The Trustees of Princeton University -- --- $Id: planetlab4.sql,v 1.47 2006/11/27 16:43:31 thierry Exp $ +-- $Id: planetlab4.sql,v 1.48 2006/11/28 10:25:03 thierry Exp $ -- -------------------------------------------------------------------------------- @@ -319,13 +319,6 @@ array_accum(node_id) AS node_ids FROM nodes GROUP BY site_id; --- Nodes at each peer -CREATE VIEW peer_nodes AS -SELECT peer_id, -array_accum(node_id) AS node_ids -FROM nodes -GROUP BY peer_id; - -------------------------------------------------------------------------------- -- Node groups -------------------------------------------------------------------------------- @@ -598,12 +591,6 @@ FROM slices WHERE is_deleted is false GROUP BY site_id; -CREATE VIEW peer_slices AS -SELECT peer_id, -array_accum(slice_id) AS slice_ids -FROM slices -GROUP BY peer_id; - -- Slice membership CREATE TABLE slice_person ( slice_id integer REFERENCES slices NOT NULL, -- Slice identifier @@ -817,6 +804,19 @@ LEFT JOIN person_sites USING (person_id) LEFT JOIN person_keys USING (person_id) LEFT JOIN person_slices USING (person_id); +-- Nodes at each peer +CREATE VIEW peer_nodes AS +SELECT peer_id, +array_accum(node_id) AS node_ids +FROM nodes +GROUP BY peer_id; + +CREATE VIEW peer_slices AS +SELECT peer_id, +array_accum(slice_id) AS slice_ids +FROM slices +GROUP BY peer_id; + CREATE VIEW view_peers AS SELECT peers.*, -- 2.43.0