Changes between Version 39 and Version 40 of AaronHelsinger/GAPI_AM_API_DRAFT


Ignore:
Timestamp:
04/02/12 12:55:40 (12 years ago)
Author:
Aaron Helsinger
Comment:

--

Legend:

Unmodified
Added
Removed
Modified
  • AaronHelsinger/GAPI_AM_API_DRAFT

    v39 v40  
    464464 3. `geni_provisioned`. The aggregate has started instantiating resources, and otherwise making changes to resources and the slice to make the resources available to the experimenter. At this point, operational states are valid to specify further when the resources are available for experimenter use.
    465465
    466 The key change is the addition of state 2, representing resources that have been allocated to a slice without provisioning the resources. This represents a cheap and un-doable resource allocation, such as we previously discussed in the context of tickets. This compares reasonably well to the 'transaction' proposal written up by Gary Wong (http://www.protogeni.net/trac/protogeni/wiki/AM_API_proposals). When a sliver is created and moved into state 2 (`geni_allocated`), the aggregate produces a manifest RSpec identifying which resources are included in the sliver. This is something like the current !CreateSlivers, except that it does not provision nor start the resources. These resources are exclusively available to the containing sliver, but are not ready for use. In particular, allocating a sliver should be a cheap and quick operation, which the aggregate can readily un-do without impacting the state of slivers which are fully provisioned. For some aggregates, transitioning to this state may be a no-op.
     466The key change is the addition of state 2, representing resources that have been allocated to a slice without provisioning the resources. This represents a cheap and un-doable resource allocation, such as we previously discussed in the context of tickets. This compares reasonably well to the 'transaction' proposal written up by Gary Wong (http://www.protogeni.net/trac/protogeni/wiki/AM_API_proposals). When a sliver is created and moved into state 2 (`geni_allocated`), the aggregate produces a manifest RSpec identifying which resources are included in the sliver. This is something like the current !CreateSliver, except that it does not provision nor start the resources. These resources are exclusively available to the containing sliver, but are not ready for use. In particular, allocating a sliver should be a cheap and quick operation, which the aggregate can readily un-do without impacting the state of slivers which are fully provisioned. For some aggregates, transitioning to this state may be a no-op.
    467467
    468468States 2 and 3 (`geni_allocated` and `geni_provisioned`) have aggregate and possibly resource specific timeouts. By convention the `geni_allocated` state timeout is typically short, like the {{{redeem_before}}} in ProtoGENI tickets, or the {{{commit_by}}} in Gary's transactions proposal. The `geni_provisioned` state timeout is the existing sliver expiration. If the client does not transition the sliver from `geni_allocated` to `geni_provisioned` before the end of the `geni_allocated` state timeout, the sliver reverts to `geni_unallocated`. If the experimenter needs more time, the experimenter should be allowed to request a renewal of either timeout.  Note that typically the sliver expiration time (timeout for state 3, `geni_provisioned`) will be notably longer than the timeout for state 2, `geni_allocated`.
    469469
    470 State 3, `geni_provisioned`, is the state of the sliver allocation after the aggregate begins to instantiate the sliver. Note that fully provisioning a sliver may take noticeable time. This state also includes a timeout - the sliver expiration time (which is not necessarily related to the time it takes to provision a resource). !RenewSlivers extends this timeout. For some aggregates and resource types, moving to this state from state 2 (`geni_allocated`) may be a no-op.
     470State 3, `geni_provisioned`, is the state of the sliver allocation after the aggregate begins to instantiate the sliver. Note that fully provisioning a sliver may take noticeable time. This state also includes a timeout - the sliver expiration time (which is not necessarily related to the time it takes to provision a resource). !RenewSliver extends this timeout. For some aggregates and resource types, moving to this state from state 2 (`geni_allocated`) may be a no-op.
    471471
    472472If the transition from one state to another fails, the sliver shall remain in its original state.
    473473
    474474These are the only allocation states supported by this API. Since the state transitions are finite, but include potentially multiple transitions between the same two states, this API uses separate methods to perform each state transition, rather than a single method for requesting a new state for the sliver.
    475  1. !CreateSlivers moves 1+ slivers from `geni_unallocated` (state 1)  to `geni_allocated` (state 2). This method can be described as creating an instance of the state machine for each sliver. If the aggregate cannot fully satisfy the request, the whole request fails. This is a change from the version 2 !CreateSliver, which also provisioned the resources, and 'started' them. That is !CreateSlivers does 1 of the 3 things that it did previously. Note the method name change, consistent with change set D.
    476  2. !DeleteSlivers moves 1+ slivers from either state 2 or 3 (`geni_allocated` or `geni_provisioned`), back to state 1 (`geni_unallocated`). This is similar to the AM API version 2 !DeleteSliver. Note the method name change, consistent with change set D.
    477  3. !RenewAllocations requests an extended timeout for slivers in state 2 (`geni_allocated`).
    478  4. !RenewSlivers requests an extended timeout for slivers in state 3 - the `geni_provisioned` state. That is, this method's semantics does not change. Note the method name change, consistent with change set D.
    479  5. !ProvisionSlivers moves 1+ slivers from state 2 (`geni_allocated`) to state 3 (`geni_provisioned`). This is some of what version 2 !CreateSliver did. Note however that this does not 'start' the resources, or otherwise change their operational state. This method only fully instantiates the resources in the slice. This may be a no-op for some aggregates or resources.
    480 
    481 '''Update''': Combine the 2 !RenewFoo methods into a single Renew() method which does different things for different sliver types.
     475 1. Allocate moves 1+ slivers from `geni_unallocated` (state 1)  to `geni_allocated` (state 2). This method can be described as creating an instance of the state machine for each sliver. If the aggregate cannot fully satisfy the request, the whole request fails. This is a change from the version 2 !CreateSliver, which also provisioned the resources, and 'started' them. That is Allocate does 1 of the 3 things that !CreateSliver did previously.
     476 2. Delete moves 1+ slivers from either state 2 or 3 (`geni_allocated` or `geni_provisioned`), back to state 1 (`geni_unallocated`). This is similar to the AM API version 2 !DeleteSliver.
     477 3. Renew, when given allocated slivers, requests an extended timeout for slivers in state 2 (`geni_allocated`).
     478 4. Renew can also be used to request an extended timeout for slivers in state 3 - the `geni_provisioned` state. That is, this method's semantics can be the same as !RenewSliver from AM API v2.
     479 5. Provision moves 1+ slivers from state 2 (`geni_allocated`) to state 3 (`geni_provisioned`). This is some of what version 2 !CreateSliver did. Note however that this does not 'start' the resources, or otherwise change their operational state. This method only fully instantiates the resources in the slice. This may be a no-op for some aggregates or resources.
    482480
    483481These states apply to each sliver individually. Logically, the state transition methods then take a single sliver URN. For convenience, these methods accept a list of sliver URNs, or a slice URN as a simple alias for all slivers in this slice at this aggregate.
     
    491489   geni_expires: <time when the sliver expires from its current state>,
    492490   <others AM or method specific>
    493    <ProvisionSlivers returns geni_operational_status>
     491   <Provision returns geni_operational_status>
    494492  },
    495493  ...
     
    497495}}}
    498496
    499 !CreateSlivers returns a single manifest RSpec, plus the above list of structs.
     497Allocate returns a single manifest RSpec, plus the above list of structs.
    500498
    501499Aggregates must be consistent across all these methods whether they are all or nothing, or support partial success.
     
    508506If the aggregate cannot guarantee all or nothing success or failure given the included slivers and resource types, the aggregate shall fail the request, returning an appropriate error code. If this option is true, then some slivers may transition to the new state, and some note. Aggregates must examine the return closely to know the state of their slivers.
    509507
    510 '''Note''': !CreateSlivers remains all or nothing (either the aggregate can allocate all desired resources as requested, or the call fails).
     508'''Note''': Allocate remains (like v2 !CreateSliver) all or nothing (either the aggregate can allocate all desired resources as requested, or the call fails).
    511509
    512510'''Note''': These calls are synchronous - when they return, the slivers shall be in their final state. In particular, the transition from state 2 to 3 (`geni_allocated` to `geni_provisioned`) should be quick. The resource that is now in the 'provisioned' state may take a long time to actually be ready for operational use (e.g. imaging and booting the node) -- this remains true as in version 2 after !CreateSliver. Note that the `geni_allocated` state is by definition cheap, such that transitioning to this state should also be quick.
     
    575573AMs may have their own operational states/state-machine internally. AMs are required to advertise such states and actions that  experimenters may see or use, by using Ad RSpec extensions. Operational states which the experimenter never sees, need not be advertised. Operational states and actions are generally by resource type. The standard RSpec extension attaches such definitions to the `sliver_type` element of RSpecs.
    576574
    577 TODO: Jon Duerig will propose this extension, with examples covering PG/Emulab sliver_types.
     575'''TODO''': Jon Duerig will propose this extension, with examples covering PG/Emulab sliver_types.
    578576
    579577Tools must use the operational states and actions advertisement to determine what operational actions to offer to  experimenters, and what actions to perform for the experimenter. Tools may choose to offer actions which the tool does not understand, relying on the experimenter to understand the meaning of the new action.
     
    888886Previously, the !CreateSliver method took a `users[]` struct to specify information for logging in to resources. But this struct is not universally applicable. This change moves that struct to be an option within the `options` struct, named `geni_users[]`.
    889887
     888== M2: Split !ListResources ==
     889Currently, !ListResources has two forms: get an advertisement general to the aggregate, and get a manifest specific to a slice. This proposal splits those two modes into two separate methods, !ListResources, and Describe.
     890
     891!ListResources would no longer take a `slice_urn` option, and no longer ever return a manifest RSpec. Describe would be used to achieve the same functionality.
     892
     893{{{
     894struct Describe(string urns[], struct credentials[], struct options[])
     895}}}
     896
     897Where options include:
     898{{{
     899{
     900  boolean geni_compressed <optional>;
     901  struct geni_rspec_version {
     902    string type;
     903    string version;
     904  };
     905}
     906}}}
     907
     908Note that all options may be omitted by the client, exception `geni_rspec_version` which is required. The aggregate must honor all supplied options.
     909
     910`credentials` is the standard argument defined elsewhere.
     911
     912Note that the manifest RSpec for allocated slivers may contain less detail than for provisioned slivers.
     913
     914Return struct:
     915{{{
     916{
     917   geni_rspec: <geni.rspec, Manifest - may be empty though)>
     918   geni_urn: <string slice urn, as requested>
     919   geni_slivers: [
     920               {
     921                  geni_sliver_urn: <string sliver urn>
     922                  geni_expires: <dateTime.rfc3339 allocation expiration string, as in geni_expires from SliversStatus>,
     923                  geni_allocation_status: <string sliver state - allocated or ?? >,
     924                  geni_operational_status: <string sliver operational state>
     925               },
     926               ...
     927         ]
     928}
     929}}}
     930
    890931-----
    891932= Changes Not Included =
     
    944985If an aggregate advertises a particular `type`/`version` (optionally defined with a combination of `schema`, `namespace` and `extensions`) in the `geni_ad_rspec_versions` attribute of !GetVersion, then it promises to send a correct Advertisement RSpec in response to a !ListResources call which supplies a `geni_rspec_version` option containing that `type`/`version`. (`geni_rspec_version` is a struct with 2 members, `type` and `version`. `type` and `version` are case-insensitive strings, matching those in `geni_ad_rspec_versions`).
    945986
    946 If an Aggregate advertises a particular `type`/`version` (optionally defined with a combination of `schema`, `namespace` and `extensions`) in the `geni_request_rspec_versions` attribute of !GetVersion then it promises to correctly honor a !CreateSliver call containing a request RSpec in the given format, and then to return a Manifest RSpec in the corresponding format (i.e. a GENI format request is answered with a GENI format manifest). The aggregate also promises to send a correctly formatted Manifest RSpec in response to a !ListResources call which supplies a valid `geni_slice_urn` option and an `geni_rspec_version` option containing that supported `type`/`version`.
     987If an Aggregate advertises a particular `type`/`version` (optionally defined with a combination of `schema`, `namespace` and `extensions`) in the `geni_request_rspec_versions` attribute of !GetVersion then it promises to correctly honor an Allocate (was !CreateSliver in API v2) call containing a request RSpec in the given format, and then to return a Manifest RSpec in the corresponding format (i.e. a GENI format request is answered with a GENI format manifest). The aggregate also promises to send a correctly formatted Manifest RSpec in response to a !ListResources call which supplies a valid `geni_slice_urn` option and an `geni_rspec_version` option containing that supported `type`/`version`.
    947988
    948989In this API, such RSpec fields are labeled as type `geni.rspec`.
     
    9921033An XML-RPC struct. For !GetVersion only, this argument is optional. In all other methods, it is required. Only !ListResources has required entries in the options struct. Aggregates are compliant with this API change by accepting this argument. Aggregates may accept entries to this struct. Aggregates should not require any new options to any method - they should always have a reasonable default for any such option. Aggregates should document new `options` arguments. The prefix `geni_` is reserved for members that are part of this API specification. Implementations should choose an appropriate prefix to avoid conflicts.
    9931034
    994 === `sliver_urns[]` ===
    995 Several methods exist in two variants. Variant one takes a slice URN. In this mode, it is interpreted to operate on all slivers contained in that slice at this aggregate. Variant two takes a list of sliver URNs. Typically, all such slivers belong to the same slice. Some aggregates may refuse calls to operate on slivers in more than one slice. All aggregates shall refuse to authorize calls which operate on more than one implicitly referenced slice but do not provide credentials that authorize operating on all such referenced slices.
     1035=== `urns[]` ===
     1036Several methods take some URNs to identify what to operate on. These methods are defined as accepting a list of arbitrary strings we call URNs.
     1037This API defines two kinds of URNs that may be supplied here, slice URNs and sliver URNs (see [wiki:GeniApiIdentifiers the GENI identifiers page], and [#Adopted:ChangeSetK:Standardizecertificatesandcredentials Change Set K]). Some aggregates may understand other URNs, but these are not defined or required here. Aggregates that accept only URNs defined by this API will return an error when given URNs not in one of those forms.
     1038This API requires that aggregates accept either a single slice URN, or 1+ sliver URNs that all belong to the same slice. Aggregates are not required to accept both a slice URN and sliver URNs, 2+ slice URNs, or a set of sliver URNs that crosses multiple slices. Some aggregates may choose to accept other such combinations of URNs. Aggregates that accept only arguments defined by this API will return an error when given more than 1 slice URN, a combination of both slice and sliver URNs, or a set of sliver URNs that belong to more than 1 slice.
    9961039
    9971040 == !GetVersion ==
     
    10821125FIXME: Break this into 3 methods: List(), List(slice), List(slivers)
    10831126
    1084  == !CreateSlivers ==
    1085 AKA Allocate()
     1127 == Allocate ==
     1128AKA !CreateSlivers()
    10861129Request resources described by the given request RSpec to be allocated to the given slice. On success, one or more slivers are allocated, containing resources satisfying the request, and assigned to the given slice. The manifest RSpec describing those resources is returned.
    10871130{{{
    1088 struct CreateSlivers(string slice_urn,
     1131struct Allocate(string slice_urn,
    10891132                    struct credentials[],
    10901133                    geni.rspec rspec,
     
    11221165Request that the named slivers be renewed, with their expiration extended. If possible, the aggregate should extend the slivers to the requested expiration time, or to a sooner time if policy limits apply. This method applies to slivers that are `geni_allocated` or to slivers that are `geni_provisioned`, though different policies may apply to slivers in the different states, resulting in much shorter max expiration times for `geni_allocated` slivers.
    11231166
    1124 This method has two forms: one takes a single slice URN, the other takes a list of one or more sliver URNs, all contained in the same slice. When a slice URN is supplied, the method operates on all slivers contained in that slice at this aggregate. All other arguments and returns are identical.
    1125 
    1126 Form 1:
    1127 {{{
    1128 struct Renew(string slice_urn,
    1129                     struct credentials[],
    1130                     dateTime.rfc3339 expiration_time,
    1131                     struct options)
    1132 }}}
    1133 
    1134 Form 2:
    1135 {{{
    1136 struct Renew(string sliver_urns[],
     1167{{{
     1168struct Renew(string urns[],
    11371169                    struct credentials[],
    11381170                    dateTime.rfc3339 expiration_time,
     
    11651197#!comment
    11661198
    1167 This method has two forms: one takes a single slice URN, the other takes a list of one or more sliver URNs, all contained in the same slice. When a slice URN is supplied, the method operates on all slivers contained in that slice at this aggregate. All other arguments and returns are identical.
    1168 
    1169 Form 1:
    1170 {{{
    1171 struct UpdateAllocations(string slice_urn, struct credentials[], geni.rspec rspec,
    1172                                 struct options)
    1173 }}}
    1174 
    1175 Form 2:
    1176 {{{
    1177 struct UpdateAllocations(string sliver_urns[], struct credentials[], geni.rspec rspec,
     1199{{{
     1200struct UpdateAllocations(string urns[], struct credentials[], geni.rspec rspec,
    11781201                                struct options)
    11791202}}}
     
    12051228}}}
    12061229
    1207  == !ProvisionSlivers ==
    1208 AKA Provision()
     1230 == Provision ==
     1231AKA !ProvisionSlivers()
    12091232Request that the named `geni_allocated` slivers be made `geni_provisioned`, instantiating or otherwise realizing the resources, such that they have a valid `geni_operational_status` and may possibly be made `geni_ready` for experimenter use.
    12101233
    1211 This method has two forms: one takes a single slice URN, the other takes a list of one or more sliver URNs, all contained in the same slice. When a slice URN is supplied, the method operates on all slivers contained in that slice at this aggregate. All other arguments and returns are identical.
    1212 
    1213 Form 1:
    1214 {{{
    1215 struct ProvisionSlivers(string slice_urn, struct credentials[], 
    1216                                    struct options)
    1217 }}}
    1218 
    1219 Form 2:
    1220 {{{
    1221 struct ProvisionSlivers(string sliver_urns[], struct credentials[], 
     1234{{{
     1235struct Provision(string urns[], struct credentials[], 
    12221236                                   struct options)
    12231237}}}
     
    12551269#!comment
    12561270
    1257 This method has two forms: one takes a single slice URN, the other takes a list of one or more sliver URNs, all contained in the same slice. When a slice URN is supplied, the method operates on all slivers contained in that slice at this aggregate. All other arguments and returns are identical.
    1258 
    1259 Form 1:
    1260 {{{
    1261 struct UpdateSlivers(string slice_urn, struct credentials[], geni.rspec rspec,
    1262                                                  struct options)
    1263 }}}
    1264 
    1265 Form 2:
    1266 {{{
    1267 struct UpdateSlivers(string sliver_urns[], struct credentials[], geni.rspec rspec,
     1271{{{
     1272struct UpdateSlivers(string urns[], struct credentials[], geni.rspec rspec,
    12681273                                                 struct options)
    12691274}}}
     
    12981303}}}
    12991304
    1300  == !SliversStatus ==
    1301 Retrieve status information about the named slivers. This should be relatively dynamic data, not descriptive data as returned in the manifest RSpec by !ListResources.
    1302 
    1303 This method has two forms: one takes a single slice URN, the other takes a list of one or more sliver URNs, all contained in the same slice. When a slice URN is supplied, the method operates on all slivers contained in that slice at this aggregate. All other arguments and returns are identical.
    1304 
    1305 Form 1:
    1306 {{{
    1307 struct SliversStatus(string slice_urn, struct credentials[], struct options)
    1308 }}}
    1309 
    1310 Form 2:
    1311 {{{
    1312 struct SliversStatus(string sliver_urns[], struct credentials[], struct options)
     1305 == Status ==
     1306AKA !SliverStatus
     1307Retrieve status information about the named slivers. This should be relatively dynamic data, not descriptive data as returned in the manifest RSpec.
     1308
     1309
     1310{{{
     1311struct Status(string urns[], struct credentials[], struct options)
    13131312}}}
    13141313
     
    13391338Perform the named operational action on the named slivers, possibly changing the `geni_operational_status` of the named slivers.
    13401339
    1341 This method has two forms: one takes a single slice URN, the other takes a list of one or more sliver URNs, all contained in the same slice. When a slice URN is supplied, the method operates on all slivers contained in that slice at this aggregate. All other arguments and returns are identical.
    1342 
    1343 Form 1:
    1344 {{{
    1345 struct PerformOperationalAction (string slice_urn, struct credentials[], string action,
    1346                                                     struct options={})
    1347 }}}
    1348 
    1349 Form 2:
    1350 {{{
    1351 struct PerformOperationalAction (string sliver_urns[], struct credentials[], string action,
     1340{{{
     1341struct PerformOperationalAction (string urns[], struct credentials[], string action,
    13521342                                                    struct options={})
    13531343}}}
     
    13701360}}}
    13711361
    1372  == !DeleteSlivers ==
     1362 == !Delete ==
     1363AKA !DeleteSliver
    13731364Delete the named slivers, making them `geni_unallocated`. Resources are de-provisioned. No further AM API operations may be performed on slivers that have been deleted.
    13741365
    1375 This method has two forms: one takes a single slice URN, the other takes a list of one or more sliver URNs, all contained in the same slice. When a slice URN is supplied, the method operates on all slivers contained in that slice at this aggregate. All other arguments and returns are identical.
    1376 
    1377 Form 1:
    1378 {{{
    1379 struct DeleteSlivers(string slice_urn, struct credentials[], struct options)
    1380 }}}
    1381 
    1382 Form 2:
    1383 {{{
    1384 struct DeleteSlivers(string sliver_urns[], struct credentials[], struct options)
     1366{{{
     1367struct Delete(string urns, struct credentials[], struct options)
    13851368}}}
    13861369