On 2013-16-09 12:03, Andy Parker wrote:
After I read your proposal, I started writing a different proposal of my
own, until I realized that it was essentially the same idea (I was just
suggesting making all of the changes to undef itself) :)

So, instead of creating a whole new proposal, I'm going to build off of
yours.

Essentially you are getting the "correct" undef semantics by creating a
new "undef" that fits the puppet language a little better. By calling it
"default" it makes the intent of it a bit clearer to users. I would like
to take things a little farther:

   * Make references of non-existent variables (no binding in the chain
of scopes) illegal

Yes + 1**10! However, doesn't this require declaring the existence of all variables? The problem is that the names of all facts are not known. Are you saying it would err on referencing such a fact? (Then I noticed you also want facts and similar to be accessed via "hash" access instead - which I like a lot, but is also a big change).

   * Remove boxing (is this boxing? I would call this coercion) of
default to other types (default != "", default != 0, default + "string"
and "$a_default_var string" is an error)

I use the term "boxing" to mean "auto coercion". But I was probably imprecise ("boxing" and "prints as" is not the same thing). Agree, the literal default is not comparable to anything but itself, the only time it becomes the string 'default' is when it is interpolated/printed.

Still, undef prints as '' so
  "What we know about bigfoot: ${facts[bigfoot]}"
results in
  'What we know about bigfoot: '

If $facts[bigfoot] == default, it would naturally have resulted in
  'What we know about bigfoot: default'

   * default is truthy (undef is falsey)
Yes, it is a value - so truthy.
Is '' truthy or falsey?

   * Preserve that default as a parameter results in the default value
of the parameter
Yes.

   * Introduce a "defaulting" operator much like perl's //
(http://perldoc.perl.org/perlop.html#Logical-Defined-Or)

We need that as a fat arrow variant, i.e. the ?>, ?=>, or perly //=> variant as this is really only needed in resource expressions.

   * Change facts and ENC variables to hashes in order to make dealing
with sometimes there, sometimes not variables easier

Yes, much better, when they are not variable references!

(I would still like facts to be declared as it makes it possible to type the facts! (A boolean fact becomes boolean, and it is possible to have (typesafe) structured facts) - that is a separate thing though.)

Now, given that you suggest making undef much stricter, which creates
compatibility problems, why bother with the default keyword? It seems
like we can achieve all of the same things that we are looking for by
just making undef stricter (remove automatic coercions, have it always
show up in ruby as nil). I like that calling it default makes intent for
the case of parameters clearer, but I fear that it ends up with a split
undefinedness problem like users of JavaScript encounter.

Not sure I completely follow the reasoning here. Literal undef evaluates to nil in ruby - yes. And just like in Ruby, when printed, it prints as an empty string ''. I would like it to not be equal to an empty string i.e. undef != '', nor equal to anything else that is empty i.e undef != [], etc, and it is not comparable (just like nil is not comparable).

JavaScript is a fantastic monstrosity of undefinedness... (a term that itself is undefined btw :-) - - -> being strict is essential.

I think introducing the defined-or operator, we can make undef behave
well, make it turn into the default in parameters, and give users
control over it when they don't want that to happen.

Then you arrived at what I first proposed - using an optional-set operator that does not set a value if it is undef. :-) If we do that we do not need literal default anywhere except as special case match expression and select match expression (what we have now).

The entire exercise with re-purposing literal default was to avoid the new operator. That was my epiphany :-)

Either way, it requires backwards incompatible changes. Dalén brought up the point that people do not want to change their manifests on an upgrade, and if they have to change, then preferably only change in a way that is backwards compatible.

To make it backwards compatible (after change) we can have a functions 'undef_as_default' that is used where the current logic wants undef to result in selection of default value - (it produces literal default when given an undef or default). Anyway, a trivial function to backport to 3.x :-)

So which do you prefer? The operator approach or the literal default approach? Or... not sure it makes sense though - use both?

- henrik

--
You received this message because you are subscribed to the Google Groups "Puppet 
Developers" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To post to this group, send email to [email protected].
Visit this group at http://groups.google.com/group/puppet-dev.
For more options, visit https://groups.google.com/groups/opt_out.

Reply via email to