Closed Bug 802839 Opened 12 years ago Closed 11 years ago

Conditional tests should only accept Boolean expressions

Categories

(L20n :: General, defect, P2)

x86_64
Linux
defect

Tracking

(Not tracked)

RESOLVED FIXED

People

(Reporter: stas, Assigned: stas)

References

Details

I'm still not sure this is the right thing thing to do, but we can discuss further in this bug.

The proposed change is to have conditional tests accept only results of expressions which return bools.

Right now, it's legal to do:

    entity ? "true" : "false"

and "entity" needs to be type-cast to a bool, which causes a lot of interesting design questions about truthiness of entities, macros, empty lists and hashes, empty objects passed to the context by the developer and others.

Instead and possibly only for 1.0, we could simply limit the spec of test conditions and explicitly require a bool expression, like so:

    entity.._gender == "feminine" ? "true" : "false"

Or:

    $unreadCount > 0 ? "some" : "zero"

instead of (currently legal and working):

    $unreadCount ? "some" : "zero"
Target Milestone: --- → 1.0
Blocks: 802843
Blocks: l20n-beta
Assignee: nobody → stas
Severity: normal → critical
Priority: -- → P2
No longer blocks: l20n-beta, 802843
I've been doing a lot of thinking about this and it continues to confuse me.  Maybe I don't understand well enough what the purpose of the grammar spec is.

Below is an excerpt from the current version of the grammar.

expression 	        : conditional_expression ;
conditional_expression 	: logical_expression WS? ( '?' WS? expression ':' WS? expression )? ;
logical_expression 	: binary_expression (WS? ('||' | '&&') WS? logical_expression)? ;
binary_expression 	: unary_expression (WS? ('==' | '!=' | ... ) WS? binary_expression)? ;
unary_expression 	: ( ('+' | '-' | '!') WS? unary_expression ) | member_expression ;
member_expression 	: call_expression | property_expression | attr_expression | parenthesis_expression ; 

I think it will be hard to change it so that all of the following statements are true:

- '!foo' and '!(foo)' are both illegal, but '!(foo == bar)' is allowed,
- 'foo == bar' is legal, but 'foo && bar' is not,
- 'foo == bar && bar == bar' is legal.

I'm leaning towards a weak typing system, where objects are implicitly converted to bools when needed.  If the rules are clear (and I'd prefer python's rules here; in particular, [] and {} are both false), I think it will be much less confusing than the proposal from comment 0.

Gandalf, Pike?
IIRC, I copied many of these concepts from a C grammar I found. That doesn't need to particularily help, just as a rationale.

I don't think we need weak types, I think we need clear conversion rules to bool, if we don't want to restructure the expression grammar. Which is the thing that we didn't want to create, hoping the expression grammar hack would be easier.

I'm not sure to which extent python rules would help us, we have things like "is foo.bar.ted true if foo is ....", with all our canonical value stuff etc. That's all stuff we can't take from python.
(In reply to Axel Hecht [:Pike] from comment #2)
> I don't think we need weak types, I think we need clear conversion rules to
> bool.

Would the conversion be implicit?

> I'm not sure to which extent python rules would help us, we have things like
> "is foo.bar.ted true if foo is ....", with all our canonical value stuff
> etc. That's all stuff we can't take from python.

I mostly meant Python's falsy-ness of [] and {}.  

From JavaScript, I'd take the falsy-ness of 'undefined' when accessing non-existing properties.  Which makes me think:  does it mean that we need True, False and None (exact names TBD)?
(In reply to Staś Małolepszy :stas from comment #3)
> (In reply to Axel Hecht [:Pike] from comment #2)
> > I don't think we need weak types, I think we need clear conversion rules to
> > bool.
> 
> Would the conversion be implicit?

I wouldn't add explicit syntax for it, if that's what you're asking.

> > I'm not sure to which extent python rules would help us, we have things like
> > "is foo.bar.ted true if foo is ....", with all our canonical value stuff
> > etc. That's all stuff we can't take from python.
> 
> I mostly meant Python's falsy-ness of [] and {}.  
> 
> From JavaScript, I'd take the falsy-ness of 'undefined' when accessing
> non-existing properties.  Which makes me think:  does it mean that we need
> True, False and None (exact names TBD)?

Probably, yes.
Flags: needinfo?(gandalf)
yup, for 1.0 I'd like to see us forbidding conversions to bool, and for next we can build clear conversion rules.

wrt. true/false/null - I'm all for it. For that we need literals.
Flags: needinfo?(gandalf)
As part of this change, we'll also want to make sure that the consequent and the alternate both evaluate to objects of the same type.
Blocks: 802843
(In reply to Zbigniew Braniecki [:gandalf] from comment #5)
> yup, for 1.0 I'd like to see us forbidding conversions to bool, and for next
> we can build clear conversion rules.

I'll fix this as part of bug 816890.

> wrt. true/false/null - I'm all for it. For that we need literals.

That's bug 816884.

(In reply to Staś Małolepszy :stas from comment #6)
> As part of this change, we'll also want to make sure that the consequent and
> the alternate both evaluate to objects of the same type.

I don't think this is currently possible.  We don't know what the consequent and the alternate evaluate to until we choose one of the paths.
Depends on: 816890
Severity: critical → normal
(In reply to Staś Małolepszy :stas from comment #7)
> I don't think this is currently possible.  We don't know what the consequent
> and the alternate evaluate to until we choose one of the paths.

Wontfix for this.

The rest landed in bug 816890.  Closing the bug.
Status: NEW → RESOLVED
Closed: 11 years ago
Resolution: --- → FIXED
You need to log in before you can comment on or make changes to this bug.