Re: Velocity truth

2017-01-30 Thread Nathan Bubna
On Mon, Jan 30, 2017 at 1:33 PM, Claude Brisson  wrote:

> On 30/01/2017 22:08, Nathan Bubna wrote:
>
> On Sat, Jan 28, 2017 at 4:38 PM, Claude Brisson 
>> wrote:
>>
>> On 28/01/2017 20:23, Alex Fedotov wrote:
>>>
>>> You guys should definitely leave a way of disabling the toString()
>>>
 conversion in boolean expressions.

 There are many places where people do null checks if #if($obj)...#end.

 Classes almost never return an empty string or null string from the
 toString  call. Even worse some classes may use toString for debugging
 purposes and produce very long  strings (including nested objects,
 etc.).
 In the code above that would be a huge inefficiency.

 I totally agree that a great percentage of #if($foo) statements are just
>>> here to check for nulls. And the current behavior of returning false for
>>> empty strings, empty arrays and empty maps could already be problematic
>>> in
>>> this regard
>>>
>>> And I think I have a good proposal about that.
>>>
>>> Since
>>>
>>> $foo differenciate null and "" (by displaying the first and not the
>>> second)
>>> $!foo assimilates null and "" (by hiding both)
>>>
>>> why not consider that:
>>>
>>> #if($foo) returns false for null and true for everything else, and
>>> #if($!foo) returns false for null, "", zero, empty arrays, etc...
>>>
>>> Yikes. That looks like a scary combo of significant and subtle. It would
>> need to be well-highlighted in the release notes, change logs, docs, etc.
>>
>> I might like it. Maybe. I dunno. The syntax is giving my tired brain
>> spasms, given that it's close to the very different #if( !$foo ). I can't
>> "read" it, if that make sense. It's like a complex regexp, where i have to
>> think my way through it, instead of just reading it.
>>
>> Is there a use-case for having both supported in the same template?
>> Otherwise, it might be better to avoid the subtlety and just support a
>> configuration property for how clever templates can be with evaluating
>> #if(
>> $foo ).
>>
>> Maybe we do the full lookup chain by default, but let people set a
>>
>> directive.if.emptycheck = false
>>
>> That would limit it to just checking for false or null values (presumably
>> still including getAsBoolean, getAsString, and toString), but skipping the
>> "empty" checks.
>>
>> Then the high performance move is:
>>
>> directive.if.emptycheck = false
>> directive.if.tostring.nullcheck = false
>>
>> But the default is for both to be true.
>>
>> That should be enough, yes.
>
> I like this syntax trick, but it remains a trick, so I won't stand for it.
> Let's forget it.
>
> However, I wonder if we should rework the lookup chain so that it never
> reaches bottom methods for standard types, collections and arrays. The
> lookup chain may pretty well mix false and true checks. Like: if it's an
> array, return whether or not it's empty and don't go further.


Good idea.  Once we find a method for checking (whether for null, false, or
empty), then we should take its answer and go no further in the chain.


Re: Velocity truth

2017-01-30 Thread Claude Brisson

On 30/01/2017 22:08, Nathan Bubna wrote:


On Sat, Jan 28, 2017 at 4:38 PM, Claude Brisson  wrote:


On 28/01/2017 20:23, Alex Fedotov wrote:

You guys should definitely leave a way of disabling the toString()

conversion in boolean expressions.

There are many places where people do null checks if #if($obj)...#end.

Classes almost never return an empty string or null string from the
toString  call. Even worse some classes may use toString for debugging
purposes and produce very long  strings (including nested objects, etc.).
In the code above that would be a huge inefficiency.


I totally agree that a great percentage of #if($foo) statements are just
here to check for nulls. And the current behavior of returning false for
empty strings, empty arrays and empty maps could already be problematic in
this regard

And I think I have a good proposal about that.

Since

$foo differenciate null and "" (by displaying the first and not the second)
$!foo assimilates null and "" (by hiding both)

why not consider that:

#if($foo) returns false for null and true for everything else, and
#if($!foo) returns false for null, "", zero, empty arrays, etc...


Yikes. That looks like a scary combo of significant and subtle. It would
need to be well-highlighted in the release notes, change logs, docs, etc.

I might like it. Maybe. I dunno. The syntax is giving my tired brain
spasms, given that it's close to the very different #if( !$foo ). I can't
"read" it, if that make sense. It's like a complex regexp, where i have to
think my way through it, instead of just reading it.

Is there a use-case for having both supported in the same template?
Otherwise, it might be better to avoid the subtlety and just support a
configuration property for how clever templates can be with evaluating #if(
$foo ).

Maybe we do the full lookup chain by default, but let people set a

directive.if.emptycheck = false

That would limit it to just checking for false or null values (presumably
still including getAsBoolean, getAsString, and toString), but skipping the
"empty" checks.

Then the high performance move is:

directive.if.emptycheck = false
directive.if.tostring.nullcheck = false

But the default is for both to be true.


That should be enough, yes.

I like this syntax trick, but it remains a trick, so I won't stand for 
it. Let's forget it.


However, I wonder if we should rework the lookup chain so that it never 
reaches bottom methods for standard types, collections and arrays. The 
lookup chain may pretty well mix false and true checks. Like: if it's an 
array, return whether or not it's empty and don't go further.


  Claude



-
To unsubscribe, e-mail: dev-unsubscr...@velocity.apache.org
For additional commands, e-mail: dev-h...@velocity.apache.org



Re: Velocity truth (was: Re: [ANNOUNCE] Velocity Engine 2.0 RC6 test build available)

2017-01-30 Thread Alex Fedotov
I guess I was not clear enough.

This option does indeed exist in 1.7. I just wanted to make sure it does
not get dropped in 2.0 as part of the cleanup work.

Alex


On Mon, Jan 30, 2017 at 4:04 PM, Nathan Bubna  wrote:

> On Mon, Jan 30, 2017 at 12:51 PM, Nathan Bubna  wrote:
>
> > On Sat, Jan 28, 2017 at 11:23 AM, Alex Fedotov  wrote:
> >
> >> You guys should definitely leave a way of disabling the toString()
> >> conversion in boolean expressions.
> >>
> >
> > Seems reasonable, and also familiar; this may have been discussed before.
> >
>
> Oh, yes, and built. I knew this was familiar. :)
>
> See http://velocity.apache.org/engine/2.0/configuration.html :
>
> directive.if.tostring.nullcheck = true
>
>
> >
> >> There are many places where people do null checks if #if($obj)...#end.
> >>
> >> Classes almost never return an empty string or null string from the
> >> toString  call. Even worse some classes may use toString for debugging
> >> purposes and produce very long  strings (including nested objects,
> etc.).
> >> In the code above that would be a huge inefficiency.
> >>
> >
> > Yes, that's part of the motive to have this lookup chain. If there's a
> > match higher up, toString() is avoided. Big deal for maps and arrays.
> >
> >
> >>
> >> Alex
> >>
> >> On Sat, Jan 28, 2017 at 2:06 PM, Nathan Bubna  wrote:
> >>
> >> > Shame that i can't remember anymore all my reasons for wanting those
> >> > "getAs" lookups. Wondering why getAsNumber and getAsBoolean are
> >> here
> >> > too. Anyone else recall the use case? And assuming that i had good
> >> reason
> >> > (that did happen sometimes ), i wonder why i pushed for bucking
> >> the
> >> > "to()" convention.
> >> >
> >> > As for the literals, the thought of them being used in #if statements
> >> in a
> >> > template language is cringe-inducing. What's the use-case? Temporary
> >> > debugging hacks? If so, part of me thinks maybe only 'true' should
> even
> >> be
> >> > allowed.
> >> >
> >> > On Sat, Jan 28, 2017 at 7:15 AM, Claude Brisson 
> >> > wrote:
> >> >
> >> > >
> >> > >
> >> >  What is the problem?
> >> > 
> >> >  Velocity "truthiness":
> >> > >>> https://issues.apache.org/jira/browse/VELOCITY-692
> >> > >>>
> >> > >>> It should definitely be part of 2.0. I missed it because the issue
> >> was
> >> > >>> closed, we should have opened a 2.0 one to remember it.
> >> > >>>
> >> > >>
> >> > >> Thats's the problem if a closed/resolved issue does not have an
> >> > >> assignee. You never know who handled it without reading the entire
> >> > >> thread. A ticket should always have an assignee if code has been
> >> > changed.
> >> > >>
> >> > >>
> >> > > Here's what had been specified by Nathan at the time (order is
> >> > meaningful,
> >> > > and falseness seems easier to specify than truth):
> >> > >
> >> > > $obj is null
> >> > > $obj is boolean false
> >> > > $obj returns false from getAsBoolean() (provided there is such a
> >> method)
> >> > > $obj is empty string (CharSequence w/length 0)
> >> > > $obj returns true from isEmpty() (provided there is such a method)
> >> > > $obj is array of length 0
> >> > > $obj returns null from getAsString() (provided there is such a
> method)
> >> > > $obj returns empty string from getAsString() (provided there is
> such a
> >> > > method)
> >> > > $obj returns null from getAsNumber() (provided there is such a
> method)
> >> > > $obj returns 0 from length() or size() (provided there is such a
> >> method)
> >> > > $obj returns empty string from toString() (provided there is such a
> >> > method)
> >> > >
> >> > > Regarding this spec:
> >> > >  - I'm not sure about getAsString() ; toString() is usually the
> >> standard
> >> > > way of getting the String representation and should be enough.
> >> > >  - I'm not convinced by the fact that zero should be true. I hear
> >> > Nathan's
> >> > > point that for a display language, zero is as legitimate as any
> other
> >> > > number to be displayed. But it breaks the principle of least
> surprise,
> >> > > since each and every other language around, when not forbidding
> number
> >> > > towards boolean implicit conversion, consider zero as false.
> >> > >
> >> > > So I'd rather go with:
> >> > >
> >> > > $obj is null
> >> > > $obj is Boolean false
> >> > > $obj is Number zero (whatever Number variant)
> >> > > $obj returns false from getAsBoolean() (provided there is such a
> >> method)
> >> > > $obj is empty string (CharSequence w/length 0)
> >> > > $obj returns true from isEmpty() (provided there is such a method)
> >> > > $obj is array of length 0
> >> > > $obj returns null from getAsNumber() (provided there is such a
> method)
> >> > > $obj returns 0 from length() or size() (provided there is such a
> >> method)
> >> > > $obj returns empty string from toString() (provided there is such a
> >> > method)
> >> > >
> >> > > Also, I noticed that Velocity weren't very 

Re: Velocity truth

2017-01-30 Thread Nathan Bubna
On Sat, Jan 28, 2017 at 4:38 PM, Claude Brisson  wrote:

> On 28/01/2017 20:23, Alex Fedotov wrote:
>
> You guys should definitely leave a way of disabling the toString()
>> conversion in boolean expressions.
>>
>> There are many places where people do null checks if #if($obj)...#end.
>>
>> Classes almost never return an empty string or null string from the
>> toString  call. Even worse some classes may use toString for debugging
>> purposes and produce very long  strings (including nested objects, etc.).
>> In the code above that would be a huge inefficiency.
>>
>
> I totally agree that a great percentage of #if($foo) statements are just
> here to check for nulls. And the current behavior of returning false for
> empty strings, empty arrays and empty maps could already be problematic in
> this regard
>
> And I think I have a good proposal about that.
>
> Since
>
> $foo differenciate null and "" (by displaying the first and not the second)
> $!foo assimilates null and "" (by hiding both)
>
> why not consider that:
>
> #if($foo) returns false for null and true for everything else, and
> #if($!foo) returns false for null, "", zero, empty arrays, etc...
>

Yikes. That looks like a scary combo of significant and subtle. It would
need to be well-highlighted in the release notes, change logs, docs, etc.

I might like it. Maybe. I dunno. The syntax is giving my tired brain
spasms, given that it's close to the very different #if( !$foo ). I can't
"read" it, if that make sense. It's like a complex regexp, where i have to
think my way through it, instead of just reading it.

Is there a use-case for having both supported in the same template?
Otherwise, it might be better to avoid the subtlety and just support a
configuration property for how clever templates can be with evaluating #if(
$foo ).

Maybe we do the full lookup chain by default, but let people set a

directive.if.emptycheck = false

That would limit it to just checking for false or null values (presumably
still including getAsBoolean, getAsString, and toString), but skipping the
"empty" checks.

Then the high performance move is:

directive.if.emptycheck = false
directive.if.tostring.nullcheck = false

But the default is for both to be true.




>   Claude
>
>
>> Alex
>>
>> On Sat, Jan 28, 2017 at 2:06 PM, Nathan Bubna  wrote:
>>
>> Shame that i can't remember anymore all my reasons for wanting those
>>> "getAs" lookups. Wondering why getAsNumber and getAsBoolean are
>>> here
>>> too. Anyone else recall the use case? And assuming that i had good reason
>>> (that did happen sometimes ), i wonder why i pushed for bucking the
>>> "to()" convention.
>>>
>>> As for the literals, the thought of them being used in #if statements in
>>> a
>>> template language is cringe-inducing. What's the use-case? Temporary
>>> debugging hacks? If so, part of me thinks maybe only 'true' should even
>>> be
>>> allowed.
>>>
>>> On Sat, Jan 28, 2017 at 7:15 AM, Claude Brisson 
>>> wrote:
>>>
>>>
 What is the problem?
>>>
>>> Velocity "truthiness":
>>>
>> https://issues.apache.org/jira/browse/VELOCITY-692
>>
>> It should definitely be part of 2.0. I missed it because the issue was
>> closed, we should have opened a 2.0 one to remember it.
>>
>> Thats's the problem if a closed/resolved issue does not have an
> assignee. You never know who handled it without reading the entire
> thread. A ticket should always have an assignee if code has been
>
 changed.
>>>

> Here's what had been specified by Nathan at the time (order is

>>> meaningful,
>>>
 and falseness seems easier to specify than truth):

 $obj is null
 $obj is boolean false
 $obj returns false from getAsBoolean() (provided there is such a method)
 $obj is empty string (CharSequence w/length 0)
 $obj returns true from isEmpty() (provided there is such a method)
 $obj is array of length 0
 $obj returns null from getAsString() (provided there is such a method)
 $obj returns empty string from getAsString() (provided there is such a
 method)
 $obj returns null from getAsNumber() (provided there is such a method)
 $obj returns 0 from length() or size() (provided there is such a method)
 $obj returns empty string from toString() (provided there is such a

>>> method)
>>>
 Regarding this spec:
   - I'm not sure about getAsString() ; toString() is usually the
 standard
 way of getting the String representation and should be enough.
   - I'm not convinced by the fact that zero should be true. I hear

>>> Nathan's
>>>
 point that for a display language, zero is as legitimate as any other
 number to be displayed. But it breaks the principle of least surprise,
 since each and every other language around, when not forbidding number
 towards boolean implicit conversion, consider zero as false.

 So I'd rather 

Re: Velocity truth (was: Re: [ANNOUNCE] Velocity Engine 2.0 RC6 test build available)

2017-01-30 Thread Nathan Bubna
On Mon, Jan 30, 2017 at 12:51 PM, Nathan Bubna  wrote:

> On Sat, Jan 28, 2017 at 11:23 AM, Alex Fedotov  wrote:
>
>> You guys should definitely leave a way of disabling the toString()
>> conversion in boolean expressions.
>>
>
> Seems reasonable, and also familiar; this may have been discussed before.
>

Oh, yes, and built. I knew this was familiar. :)

See http://velocity.apache.org/engine/2.0/configuration.html :

directive.if.tostring.nullcheck = true


>
>> There are many places where people do null checks if #if($obj)...#end.
>>
>> Classes almost never return an empty string or null string from the
>> toString  call. Even worse some classes may use toString for debugging
>> purposes and produce very long  strings (including nested objects, etc.).
>> In the code above that would be a huge inefficiency.
>>
>
> Yes, that's part of the motive to have this lookup chain. If there's a
> match higher up, toString() is avoided. Big deal for maps and arrays.
>
>
>>
>> Alex
>>
>> On Sat, Jan 28, 2017 at 2:06 PM, Nathan Bubna  wrote:
>>
>> > Shame that i can't remember anymore all my reasons for wanting those
>> > "getAs" lookups. Wondering why getAsNumber and getAsBoolean are
>> here
>> > too. Anyone else recall the use case? And assuming that i had good
>> reason
>> > (that did happen sometimes ), i wonder why i pushed for bucking
>> the
>> > "to()" convention.
>> >
>> > As for the literals, the thought of them being used in #if statements
>> in a
>> > template language is cringe-inducing. What's the use-case? Temporary
>> > debugging hacks? If so, part of me thinks maybe only 'true' should even
>> be
>> > allowed.
>> >
>> > On Sat, Jan 28, 2017 at 7:15 AM, Claude Brisson 
>> > wrote:
>> >
>> > >
>> > >
>> >  What is the problem?
>> > 
>> >  Velocity "truthiness":
>> > >>> https://issues.apache.org/jira/browse/VELOCITY-692
>> > >>>
>> > >>> It should definitely be part of 2.0. I missed it because the issue
>> was
>> > >>> closed, we should have opened a 2.0 one to remember it.
>> > >>>
>> > >>
>> > >> Thats's the problem if a closed/resolved issue does not have an
>> > >> assignee. You never know who handled it without reading the entire
>> > >> thread. A ticket should always have an assignee if code has been
>> > changed.
>> > >>
>> > >>
>> > > Here's what had been specified by Nathan at the time (order is
>> > meaningful,
>> > > and falseness seems easier to specify than truth):
>> > >
>> > > $obj is null
>> > > $obj is boolean false
>> > > $obj returns false from getAsBoolean() (provided there is such a
>> method)
>> > > $obj is empty string (CharSequence w/length 0)
>> > > $obj returns true from isEmpty() (provided there is such a method)
>> > > $obj is array of length 0
>> > > $obj returns null from getAsString() (provided there is such a method)
>> > > $obj returns empty string from getAsString() (provided there is such a
>> > > method)
>> > > $obj returns null from getAsNumber() (provided there is such a method)
>> > > $obj returns 0 from length() or size() (provided there is such a
>> method)
>> > > $obj returns empty string from toString() (provided there is such a
>> > method)
>> > >
>> > > Regarding this spec:
>> > >  - I'm not sure about getAsString() ; toString() is usually the
>> standard
>> > > way of getting the String representation and should be enough.
>> > >  - I'm not convinced by the fact that zero should be true. I hear
>> > Nathan's
>> > > point that for a display language, zero is as legitimate as any other
>> > > number to be displayed. But it breaks the principle of least surprise,
>> > > since each and every other language around, when not forbidding number
>> > > towards boolean implicit conversion, consider zero as false.
>> > >
>> > > So I'd rather go with:
>> > >
>> > > $obj is null
>> > > $obj is Boolean false
>> > > $obj is Number zero (whatever Number variant)
>> > > $obj returns false from getAsBoolean() (provided there is such a
>> method)
>> > > $obj is empty string (CharSequence w/length 0)
>> > > $obj returns true from isEmpty() (provided there is such a method)
>> > > $obj is array of length 0
>> > > $obj returns null from getAsNumber() (provided there is such a method)
>> > > $obj returns 0 from length() or size() (provided there is such a
>> method)
>> > > $obj returns empty string from toString() (provided there is such a
>> > method)
>> > >
>> > > Also, I noticed that Velocity weren't very consistent with literals.
>> The
>> > > only literal returning true is the 'true' literal. "foo" is false,
>> > whereas
>> > > it should be consistent with $foo containing "foo".
>> > >
>> > >   Claude
>> > >
>> > >
>> > > -
>> > > To unsubscribe, e-mail: dev-unsubscr...@velocity.apache.org
>> > > For additional commands, e-mail: dev-h...@velocity.apache.org
>> > >
>> > >
>> >
>>
>
>


Re: Velocity truth (was: Re: [ANNOUNCE] Velocity Engine 2.0 RC6 test build available)

2017-01-30 Thread Nathan Bubna
On Sat, Jan 28, 2017 at 11:23 AM, Alex Fedotov  wrote:

> You guys should definitely leave a way of disabling the toString()
> conversion in boolean expressions.
>

Seems reasonable, and also familiar; this may have been discussed before.


> There are many places where people do null checks if #if($obj)...#end.
>
> Classes almost never return an empty string or null string from the
> toString  call. Even worse some classes may use toString for debugging
> purposes and produce very long  strings (including nested objects, etc.).
> In the code above that would be a huge inefficiency.
>

Yes, that's part of the motive to have this lookup chain. If there's a
match higher up, toString() is avoided. Big deal for maps and arrays.


>
> Alex
>
> On Sat, Jan 28, 2017 at 2:06 PM, Nathan Bubna  wrote:
>
> > Shame that i can't remember anymore all my reasons for wanting those
> > "getAs" lookups. Wondering why getAsNumber and getAsBoolean are
> here
> > too. Anyone else recall the use case? And assuming that i had good reason
> > (that did happen sometimes ), i wonder why i pushed for bucking the
> > "to()" convention.
> >
> > As for the literals, the thought of them being used in #if statements in
> a
> > template language is cringe-inducing. What's the use-case? Temporary
> > debugging hacks? If so, part of me thinks maybe only 'true' should even
> be
> > allowed.
> >
> > On Sat, Jan 28, 2017 at 7:15 AM, Claude Brisson 
> > wrote:
> >
> > >
> > >
> >  What is the problem?
> > 
> >  Velocity "truthiness":
> > >>> https://issues.apache.org/jira/browse/VELOCITY-692
> > >>>
> > >>> It should definitely be part of 2.0. I missed it because the issue
> was
> > >>> closed, we should have opened a 2.0 one to remember it.
> > >>>
> > >>
> > >> Thats's the problem if a closed/resolved issue does not have an
> > >> assignee. You never know who handled it without reading the entire
> > >> thread. A ticket should always have an assignee if code has been
> > changed.
> > >>
> > >>
> > > Here's what had been specified by Nathan at the time (order is
> > meaningful,
> > > and falseness seems easier to specify than truth):
> > >
> > > $obj is null
> > > $obj is boolean false
> > > $obj returns false from getAsBoolean() (provided there is such a
> method)
> > > $obj is empty string (CharSequence w/length 0)
> > > $obj returns true from isEmpty() (provided there is such a method)
> > > $obj is array of length 0
> > > $obj returns null from getAsString() (provided there is such a method)
> > > $obj returns empty string from getAsString() (provided there is such a
> > > method)
> > > $obj returns null from getAsNumber() (provided there is such a method)
> > > $obj returns 0 from length() or size() (provided there is such a
> method)
> > > $obj returns empty string from toString() (provided there is such a
> > method)
> > >
> > > Regarding this spec:
> > >  - I'm not sure about getAsString() ; toString() is usually the
> standard
> > > way of getting the String representation and should be enough.
> > >  - I'm not convinced by the fact that zero should be true. I hear
> > Nathan's
> > > point that for a display language, zero is as legitimate as any other
> > > number to be displayed. But it breaks the principle of least surprise,
> > > since each and every other language around, when not forbidding number
> > > towards boolean implicit conversion, consider zero as false.
> > >
> > > So I'd rather go with:
> > >
> > > $obj is null
> > > $obj is Boolean false
> > > $obj is Number zero (whatever Number variant)
> > > $obj returns false from getAsBoolean() (provided there is such a
> method)
> > > $obj is empty string (CharSequence w/length 0)
> > > $obj returns true from isEmpty() (provided there is such a method)
> > > $obj is array of length 0
> > > $obj returns null from getAsNumber() (provided there is such a method)
> > > $obj returns 0 from length() or size() (provided there is such a
> method)
> > > $obj returns empty string from toString() (provided there is such a
> > method)
> > >
> > > Also, I noticed that Velocity weren't very consistent with literals.
> The
> > > only literal returning true is the 'true' literal. "foo" is false,
> > whereas
> > > it should be consistent with $foo containing "foo".
> > >
> > >   Claude
> > >
> > >
> > > -
> > > To unsubscribe, e-mail: dev-unsubscr...@velocity.apache.org
> > > For additional commands, e-mail: dev-h...@velocity.apache.org
> > >
> > >
> >
>