-
Notifications
You must be signed in to change notification settings - Fork 27
Description
There is a mismatch in how es parses %closures and how it prints them.
%closures are parsed exactly the same way as let, local, and for statements: they are special kinds of command, which are only parsed specially when placed in head position.
However, %closures are printed like special thunks or lambdas, where they are treated as specific kinds of words.
This mismatch produces the following unhappiness:
; let (a = b) th = {~ $a b}
; let (a = c) echo if $th {echo $a}
if %closure(a=b){~ $a b} %closure(a=c){echo $a}
; if %closure(a=b){~ $a b} %closure(a=c){echo $a}
%closure:1: syntax error
I think this is wrong; in principle, es shouldn't print commands in a way that it can't parse them back in. So I think there are two possible ways to fix this:
- Parse
%closureas a word so that es understands it anywhere in a command - Format
%closurein a way that works as a command
Initially I assumed option 1 was the only real fix, since (as in the above example) it's very possible to have a single command with multiple incompatible closures over different terms. However, in theory you can do option 2, if you wrap things in enough thunks, such that the above problematic command becomes
if {%closure(a=b){~ $a b}} {%closure(a=c){echo $a}}
We could then make this read even nicer in my opinion if we got rid of the %closure syntax completely and just used let:
if {let(a=b){~ $a b}} {let(a=c){echo $a}}
Of course, this would be a backwards-incompatible change, as we'd be removing a previously valid syntax from the shell.
The first option would also be slightly backwards-incompatible. Since we'd be changing %closure() from a command construct to a word construct, commands like %closure(a=b)echo $a would parse differently than they do now.
I've hacked up both of these options. The first option seems to work fine, even with a pretty quick-and-dirty implementation, though I do think it's a little bit ugly; a similarly quick hack of the second option seems to cause mysterious segfaults, due potentially to subtleties with %closure that I don't understand.