[openstack-dev] [Heat] RPC API versioning
Zane Bitter
zbitter at redhat.com
Thu Aug 6 00:57:24 UTC 2015
We've been talking about this since before summit without much
consensus. I think a large part of the problem is that very few people
have deep knowledge of both Heat and Versioned Objects. However, I think
we are at a point where we should be able to settle on an approach at
least for the API<->engine RPC interface. I've been talking to Dan Smith
about the Nova team's plan for upgrades, which goes something like this:
* Specify a max RPC API version in the config file
* In the RPC client lib, add code to handle versions as far back as the
previous release
* The operator rolls out the updated code, keeping the existing config
file with the pin to the previous release's RPC version
* Once all services are upgraded, the operator rolls out a new config
file shifting the pin
* The backwards compat code to handle release N-1 is removed in the N+1
release
This is, I believe, sufficient to solve our entire problem.
Specifically, we have no need for an indirection API that rebroadcasts
messages that are too new (since that can't happen with pinning) and no
need for Versioned Objects in the RPC layer. (Versioned objects for the
DB are still critical, and we are very much better off for all the hard
work that Michal and others have put into them. Thanks!)
The nature of Heat's RPC API is that it is effectively user-facing - the
heat-api process is essentially a thin proxy between ReST and RPC. We
already have a translation layer between the internal representation(s)
of objects and the user-facing representation, in the form of
heat.engine.api, and the RPC API is firmly on the user-facing side. The
requirements for the content of these messages are actually much
stricter than anything we need for RPC API stability, since they need to
remain compatible not just with heat-api but with heatclient - and we
have *zero* control over when that gets upgraded. Despite that, we've
managed quite nicely for ~3 years without breaking changes afaik.
Versioned Objects is a great way of retaining control when you need to
share internal data structures between processes. Fortunately the
architecture of Heat makes that unnecessary. That was a good design
decision. We are not going to reverse that design decision in order to
use Versioned Objects. (In the interest of making sure everyone uses
their time productively, perhaps I should clarify that to: "your patch
is subject to -2 on sight if it introduces internal engine data
structures to heat-api/heat-cfn-api".)
Hopefully I've convinced you of the sufficiency of this plan for the
API<->engine interface specifically. If anyone disagrees, let them speak
now, &c.
I think there is still a case that could be made for a different
approach to the RPC API for convergence, which is engine->engine and
(probably) doesn't yet have a formal translation layer of the same kind.
At a minimum, obviously, we should do the same stuff listed above
(though I don't think we need to declare that interface stable until the
first release where we enable convergence by default).
There's probably places where versioned objects could benefit us. For
example, when we trigger a check on a resource we pass it a bundle of
data containing all the attributes and IDs it might need from resources
it depends on. It definitely makes sense to me that that bundle would be
a Versioned Object. (In fact, that data gets stored in the DB - as
SyncPoint in the prototype - so we wouldn't even need to create a new
object type. This seems like a clear win.)
What I do NOT want to do is to e.g. replace the resource_id of the
resource to check with a versioned object containing the DB
representation of a resource. In most cases that doesn't save a DB
lookup, it just moves it to the other end of the RPC call. And as long
as primary keys are unique, this can never create a compatibility problem :)
Grzegorz mentioned in https://review.openstack.org/#/c/196670/ the
possibility of using the indirection API to handle changes to the
message format - I guess this is an alternative to the version pinning
approach mentioned by Dan? I'm currently leaning toward thinking that
this is unnecessary, but I'm not sure I understand it completely so I'd
need to see a patch to form an opinion. I'm wide open to persuasion on
this part. However I'd be opposed to this *replacing* (rather than
supplementing) the version pinning behaviour described above - the whole
retransmission of too-new messages thing sounds like it could have any
number of pathological corner cases and I'd prefer to avoid it.
cheers,
Zane.
More information about the OpenStack-dev
mailing list