-
Notifications
You must be signed in to change notification settings - Fork 47
[epic] Rework params to support xpath-like replacing and non-scalar values #70
Comments
Related #64 |
do you guys think we should put that in the Summit release? I think so... |
I think so too |
If possible. I sure would like it as soon as is reasonable. On Wed, May 20, 2015 at 2:28 PM, Vaclav Pavlin notifications@github.com
Mark Lamourine markllama@gmail.com |
Just wondering - why does the
|
I am wondering the very same thing atm as I was looking at rework of atomicapp to comply with 0.0.2 - we changed components and params to be a list to get rid of magic keys..shouldn't we do the same for providers? Although that would have to be
@aweiteka @goern Are you ok with using provider names as keys here? Or should we also change it to a list? |
using names as keys breaks schema validation, doesn't it? array of things with one attribute "name: foo" or .... .not sure On Thu, May 21, 2015 at 12:49 PM, Vaclav Pavlin notifications@github.com
Mark Lamourine markllama@gmail.com |
ja, there shall be no magic key as of #35 |
Python implementation of json pointers - https://pypi.python.org/pypi/jsonpointer |
since rfc6901 is a fragment identifier specification, I would really suggest for standard and potential future uses to use the syntax # for specifying the path: This means in URI terms, take the current document and extract the following fragment identifier. |
This has the potential to break multi-provider support. Perhaps we should consider a two-level process. The Nulecule file remains a key/value structure like today. Each provider needs to provide a transformation matrix that translates the keys from the Nulecule file to their pointers (or other method) for the specific provider. It creates more work for application providers, but retains easy use by end-users with single and multiple providers. This means we may need to define built-in transformers (probably xslt or something similar for json, and $XX substitution for docker) and the ability to load an external transformer from a container for more esoteric types. |
@bexelbie I think you nailed it.
Fleshing this out from our conversation... Given Nulecule file
File
|
Above I proposed putting the provider param translation in another file. This is problematic since we would probably need to agree on a naming convention and it abstracts the parameters making it difficult to develop since the params are referenced in two different files. A more compact way would be to refactor the artifacts object so it has more structure than just a list of files. This would allow us to embed the params mapping into the artifacts object. Something like this:
cc @veillard |
Seeing urges me to simplify it to And you have something which is a proper URI Daniel |
That does seem appealing and I think we should support that so params can be targeted to an exact thing using fully qualified URI. The trouble I see with this is...
One of the use cases I'm considering is there may be multiple places to reference a single param value. This is not possible with the list of key:value pairs suggested here. A way to approach this could be to us a list of pointers under each param name key. For example...
|
One nasty thing is that referencing local files is always a bit of a mess, file:// scheme works fine for absolute patch but in practice it's rarely where the files sits. The RFC for file:// is (was) a big mess for anything not an absolute path, so you end up forgetting the scheme and doing things like Since we need to keep $ based substitution anyway, we could just make source optional for pointers. |
@veillard I am not sure f I understand what you are proposing/suggesting in your comment - |
no solution, just a warning. for example file:/../foo vs. file:///../foo will get probably more confusion |
Hum, params should really be associated to a given source. If you start giving multiple sources in the
and then we need to check the resource is in the provided list of sources,
|
Maybe don't use array for params as the keys are not really "magic keys" we want to avoid but has to exist in
|
Yeah that works artifacts/kubernetes/template.json#/spec/template/metadata/foo is more web like but it can get repetitive and we already need to provide the URI for the |
New Nulecule_Base methods for getting and templating artifacts were added. These are backwards compatible with pre-xpath implementation. New format for artifacts is described in: projectatomic/nulecule#70 (comment) Fixes projectatomic#192
We need to update the spec. |
@charliedrage I think the only change is to the params object: |
Awesome, I'll send in a PR :) thanks @aweiteka ! |
Problem statement
Currently params work with simple substitution. You need to specify the param name prefixed with
$
in the artifact and it's then replaced with the value given either by default, answers file or by the user in case of interactive mode. This is a problem because a developer of nulecule application has to modify (upstream) kube files and replace real values with something like$image
. This brings debuging problems right now (you cannot use artifacts shipped in nulecule app directly) and will bring a lot of maintainance problems in the future (you need to mirror all changes in upstream artifacts in your modified files).Based on the description in previous paragraph it is obvious (almost) all artifacts has to be modified from upstream and thus maintained directly in the nulecule app repo - i.e. it does not make much sense to reference artifacts by remote URL (https://...) and deffer their download to the point of installation.
Also there already were some discussions about supporting non-scalar types, thus part of this proposal is addition of
type
key to the params definition.Proposal
JSON Pointer
Based on an idea of @markllama we came to the conclusion we need to be able to replace param values in artifacts not based on the placeholder, but based on the position in the json/yaml object. This will enable developers of nulecule applications to exactly specify what should be replaced without a need to modify the artifacts.
This concept is described in a JSON Pointer (https://tools.ietf.org/html/rfc6901)
For this kubernetes pod definition
The param
image
should look likeAs you can see,
pointer
is defined as an array which means you can specify more places in an artifact(s) where the param should be used. Also thedefault
is optional and if not specified (i.e. if the keydefault
is omitted) the actual value in artifact can be used. Existing keydefault
set tonull
means that a user needs to provide the value in answers.Although using the
pointer
will be strongly recommended, current substitution of$
prefixed variables will continue to work as there might be some use cases for it.To preserve the simplicity of answers file, params will be refferenced by name there. On the other hand extension to support JSON Pointer notaition as keys in answers file should be simple (and would potentially enable user to replace not only the given params, but, for debugging purposes, any value in any artifact)
Problems
Same JSON Pointer path might exist in multiple artifacts although user might want to change the value only in a single specific artifact
Exact location specified by JSON Pointer might lead to failing runs in case of unexpected changes in artifact.
f.e.
value
of environment variablePASS
specified in kubernetes pod definition:would have path
.../containers/env/1/value
. If upstream decides to add environment variableFOO
above thePASS
variable, the path toPASS
changes to.../containers/env/2/value
(note the change1 -> 2
).Allow URL and git description for artifacts
Although specification does not block anybody from specifying remote location, current implementation and the way how we substitute params basically supports only artifacts stored locally. As a part of this proposal we should document ability of the spec to accept remote locations for artifacts - i.e.
I'd also like to propose a special type of artifact which would be specified by object in a format similar to:
Where
git clone
commandgit checkout
commandcd
command (all files found in that directory are then expected to be artifacts)Artifacts can be then specified by a combination by URL like strings and above specified objects describing contents of git repository.
Problems
The only problem I can think of regarding this change is potentially conflicting file names. This is not really a spec problem, but mostly an implementation problem thus at least some naming suggestions might be provided to developers.
Add
type
to the params definitionCurrently we use
INI
format to storeanswers.conf(.sample)
. Although this is nice from user experience point of view, it blocks us from using non-scalar values for params as is.Let's assume we have an application which expects a list of IP addresses as a parameter. With current params structure and
INI
file it's not possible to parse and pass such value to the Nulecule app without assumptions being done about the param - i.e. mathing the value to some regular expressions or something similar. In case of adding atype
key to params definition we would be able to recognize the value type easily and by parsing it also validate it against the giventype
.For
yaml
andjson
types are implicit, forINI
we would need to introduce some conventions - f.e.:The
type
key might be optional and default to current behaviour - i.e. typestring
.Problems
This would obviously bring more complexity to both implementation of the spec and creation of nulecule apps.
The text was updated successfully, but these errors were encountered: