from __future__ import with_statement
-from sfa.util.faults import *
-from sfa.util.namespace import *
-from sfa.util.rspec import RSpec
-from sfa.server.registry import Registries
-from sfa.plc.nodes import *
+
+import sys
+import os
import boto
from boto.ec2.regioninfo import RegionInfo
from lxml import etree as ET
from sqlobject import *
-import sys
-import os
+from sfa.util.faults import *
+from sfa.util.namespace import urn_to_hrn
+from sfa.util.rspec import RSpec
+from sfa.server.registry import Registries
##
# The data structure used to represent a cloud.
return clusterList
-def get_rspec(api, xrn, origin_hrn):
+def get_rspec(api, creds, options):
global cloud
- hrn = urn_to_hrn(xrn)[0]
+ # get slice's hrn from options
+ xrn = options.get('geni_slice_urn', None)
+ hrn, type = urn_to_hrn(xrn)
+
+ # get hrn of the original caller
+ origin_hrn = options.get('origin_hrn', None)
+ if not origin_hrn:
+ origin_hrn = Credential(string=creds[0]).get_gid_caller().get_hrn()
+
conn = getEucaConnection()
if not conn:
# Get the instances that belong to the given slice from sqlite3
# XXX use getOne() in production because the slice's hrn is supposed
# to be unique. For testing, uniqueness is turned off in the db.
- theSlice = list(Slice.select(Slice.q.slice_hrn == hrn))[-1]
+ # If the slice isn't found in the database, create a record for the
+ # slice.
+ matchedSlices = list(Slice.select(Slice.q.slice_hrn == hrn))
+ if matchedSlices:
+ theSlice = matchedSlices[-1]
+ else:
+ theSlice = Slice(slice_hrn = hrn)
for instance in theSlice.instances:
instanceId.append(instance.instance_id)
# Get the information about those instances using their ids.
- reservations = conn.get_all_instances(instanceId)
+ if len(instanceId) > 0:
+ reservations = conn.get_all_instances(instanceId)
+ else:
+ reservations = []
for reservation in reservations:
for instance in reservation.instances:
instances.append(instance)
rspec = EucaRSpecBuilder(cloud).toXML()
+ # Remove the instances records so next time they won't
+ # show up.
+ if 'instances' in cloud:
+ del cloud['instances']
+
return rspec
"""
Hook called via 'sfi.py create'
"""
-def create_slice(api, xrn, xml):
+def create_slice(api, xrn, creds, xml, users):
global cloud
hrn = urn_to_hrn(xrn)[0]
print >>sys.stderr, 'Error: Cannot create a connection to Eucalyptus'
return False
- # Get the slice from db or create one.
- # XXX: For testing purposes, I'll just create the slice.
- #s = Slice.select(Slice.q.slice_hrn == hrn).getOne(None)
- #if s is None:
- s = Slice(slice_hrn = hrn)
-
# Validate RSpec
schemaXML = ET.parse(EUCALYPTUS_RSPEC_SCHEMA)
rspecValidator = ET.RelaxNG(schemaXML)
if not rspecValidator(rspecXML):
error = rspecValidator.error_log.last_error
message = '%s (line %s)' % (error.message, error.line)
- raise InvalidRSpec(message)
+ # XXX: InvalidRSpec is new. Currently, I am not working with Trunk code.
+ #raise InvalidRSpec(message)
+ raise Exception(message)
- # Process the RSpec
+ # Get the slice from db or create one.
+ s = Slice.select(Slice.q.slice_hrn == hrn).getOne(None)
+ if s is None:
+ s = Slice(slice_hrn = hrn)
+
+ # Process any changes in existing instance allocation
+ pendingRmInst = []
+ for sliceInst in s.instances:
+ pendingRmInst.append(sliceInst.instance_id)
+ existingInstGroup = rspecXML.findall('.//euca_instances')
+ for instGroup in existingInstGroup:
+ for existingInst in instGroup:
+ if existingInst.get('id') in pendingRmInst:
+ pendingRmInst.remove(existingInst.get('id'))
+ for inst in pendingRmInst:
+ print >>sys.stderr, 'Instance %s will be terminated' % inst
+ dbInst = EucaInstance.select(EucaInstance.q.instance_id == inst).getOne(None)
+ dbInst.destroySelf()
+ conn.terminate_instances(pendingRmInst)
+
+ # Process new instance requests
requests = rspecXML.findall('.//request')
for req in requests:
vmTypeElement = req.getparent()
def main():
init_server()
- #theRSpec = None
- #with open(sys.argv[1]) as xml:
- #theRSpec = xml.read()
- #create_slice(None, 'planetcloud.pc.test', theRSpec)
+ theRSpec = None
+ with open(sys.argv[1]) as xml:
+ theRSpec = xml.read()
+ create_slice(None, 'planetcloud.pc.test', theRSpec)
- rspec = get_rspec('euca', 'planetcloud.pc.test', 'planetcloud.pc.marcoy')
- print rspec
+ #rspec = get_rspec('euca', 'planetcloud.pc.test', 'planetcloud.pc.marcoy')
+ #print rspec
if __name__ == "__main__":
main()