On 23/03/16 13:14, Steven Hardy wrote:
Hi all,

I'm looking for some help and additional input on this bug:

https://bugs.launchpad.net/heat/+bug/1559807

Hmm, I was wondering how this ever worked, but it appears you're making particularly aggressive use of the list_join and map_merge Functions there - where you're not only getting the elements in the list of things to merge (as presumably originally envisioned) but actually getting the list itself from an intrinsic function. If we're going to support that then those functions need to handle the fact that the input argument may be None, just as they do for the list members (see the ensure_string() and ensure_map() functions inside the result() methods of those two Functions).

Basically, we have multiple issues due to the fact that we consider
get_attr to resolve to None at any point before a resource is actually
instantiated.

It's due to this:

https://github.com/openstack/heat/blob/master/heat/engine/hot/functions.py#L163

This then causes problems during validation of several intrinsic functions,
because if they reference get_attr, they have to contain hacks and
special-cases to work around the validate-time None value (or, as reported
in the bug, fail to validate when all would be fine at runtime).

https://github.com/openstack/heat/blob/master/heat/engine/resource.py#L1333

I started digging into fixes, and there are probably a few possible
approaches, e.g setting stack.Stack.strict_validate always to False, or
reworking the intrinsic function validation to always work with the
temporary None value.

However, it's a more widespread issue than just validation - this affects
any action which happens before the actual stack gets created, so things
like preview updates are also broken, e.g consider this:

resources:
   random:
     type: OS::Heat::RandomString

   config:
     type: OS::Heat::StructuredConfig
     properties:
       group: script
       config:
         foo: {get_attr: [random, value]}

   deployment:
     type: OS::Heat::StructuredDeployment
     properties:
       config:
         get_resource: config
       server: "dummy"

On update, nothing is replaced, but if you do e.g:

   heat stack-update -x --dry-run

You see this:

| replaced  | config        | OS::Heat::StructuredConfig     |

Which occurs due to the false comparison between the current value of
"random" and the None value we get from get_attr in the temporary stack
used for preview comparison:

https://github.com/openstack/heat/blob/master/heat/engine/resource.py#L528

after_props.get(key) returns None, which makes us falsely declare the
"config" resource gets replaced :(

I'm looking for ideas on how we solve this - it's clearly a major issue
which completely invalidates the results of validate and preview operations
in many cases.

I've been thinking about this (for about 2 years).

My first thought (it seemed like a good idea at the time, 2 years ago, for some reason) was for Function objects themselves to take on the types of their return values, so e.g. a Function returning a list would have a __getitem__ method and generally act like a list. Don't try this at home, BTW, it doesn't work.

I now think the right answer is to return some placeholder object (but not None). Then the validating code can detect the placeholder and do some checks. e.g. we would be able to say that the placeholder for get_resource on a Cinder volume would have type 'cinder.volume' and any property with a custom constraint would check that type to see if it matches (and fall back to accepting any text type if the placeholder doesn't have a type associated). get_param would get its type from the parameter schema (including any custom constraints). For get_attr we could make it part of the attribute schema.

The hard part obviously would be getting this to work with deeply-nested trees of data and across nested stacks. We could probably get the easy parts going and incrementally improve from there though. Worst case we just return None and get the same behaviour as now.

cheers,
Zane.

__________________________________________________________________________
OpenStack Development Mailing List (not for usage questions)
Unsubscribe: [email protected]?subject:unsubscribe
http://lists.openstack.org/cgi-bin/mailman/listinfo/openstack-dev

Reply via email to