-
Notifications
You must be signed in to change notification settings - Fork 164
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
spec: convergence with Go #20
Comments
Is there more context on this? I've found it exceedingly convenient to use Python's |
The key word in this sentence is "convenient". :) If you want to transform a Starlark program from Python, the right thing to do is write a Starlark parser in Python. It should be easy because you can just fork the Python parser and delete the parts you don't need. The syntax of Starlark is, for now, a subset of Python, but longer term it could be improved by breaking compatibility. The most glaring problem is the syntax for load, which must use strings where identifiers are wanted. Tools that assume a Python parser is sufficient are taking an expedient short-cut at the expense of long term maintainability, which is the definition of a hack. The Bazel test tools I was alluding to go one step further and actually execute the Skylark program in a Python interpreter, which is very fragile indeed. |
I met with Laurent and Damien today and we agreed on the following spec changes:
|
...unless -globalreassign is set. Formerly, the Go implementation permitted x+=y on the basis that we couldn't statically tell whether x was a list (in which case x+=y means x.extend(y), which is not a rebinding), or some other type, in which case it is a forbidden rebinding. This change makes it match the Java implementation. See bazelbuild/starlark#20 (comment) Most non-Bazel-like clients of Starlark set the -globalreassign flag. Change-Id: I1a21fc6871e51c201529da91dc0a46ad3e99d448
...unless -globalreassign is set. Formerly, the Go implementation permitted x+=y on the basis that we couldn't statically tell whether x was a list (in which case x+=y means x.extend(y), which is not a rebinding), or some other type, in which case it is a forbidden rebinding. This change makes it match the Java implementation. See bazelbuild/starlark#20 (comment) Most non-Bazel-like clients of Starlark set the -globalreassign flag. Change-Id: I9bb508255dcf66594a025df01db82901fc7742cc
...unless -globalreassign is set. Formerly, the Go implementation permitted x+=y on the basis that we couldn't statically tell whether x was a list (in which case x+=y means x.extend(y), which is not a rebinding), or some other type, in which case it is a forbidden rebinding. This change makes it match the Java implementation. See bazelbuild/starlark#20 (comment) Most non-Bazel-like clients of Starlark set the -globalreassign flag. Change-Id: Ife0df4776da27762dbaf34228f926caf7777c2aa
...unless -globalreassign is set. Formerly, the Go implementation permitted x+=y on the basis that we couldn't statically tell whether x was a list (in which case x+=y means x.extend(y), which is not a rebinding), or some other type, in which case it is a forbidden rebinding. This change makes it match the Java implementation. See bazelbuild/starlark#20 (comment) Most non-Bazel-like clients of Starlark set the -globalreassign flag. Change-Id: I5477c46c3d4e00dad419528ee2953b8bd6b47a26
See bazelbuild/starlark#20 (comment) Change-Id: I595f87b9b777e79065684ee2c29acb6435b232cf
...unless -globalreassign is set. Formerly, the Go implementation permitted x+=y on the basis that we couldn't statically tell whether x was a list (in which case x+=y means x.extend(y), which is not a rebinding), or some other type, in which case it is a forbidden rebinding. This change makes it match the Java implementation. See bazelbuild/starlark#20 (comment) Most non-Bazel-like clients of Starlark set the -globalreassign flag.
Implements: bazelbuild/starlark#20 (comment) Closes #8890. PiperOrigin-RevId: 258388687
Implement:bazelbuild/starlark#20 (comment) Closes #8881. PiperOrigin-RevId: 258401453
…sing getattr Related: bazelbuild/starlark#20 (comment), #5224 It's now possible to call methods in two steps `y = x.f; y()` Also, `getattr` can now be used to retrieve built-in methods. Closes #8931. PiperOrigin-RevId: 259711316
Add support for `~`, `&`, `|`, `^`, `<<`, `>>` bitwise operations. Implements: bazelbuild/starlark#20 (comment) Closes #8903. PiperOrigin-RevId: 259732302
Update: These are all done, except:
|
Updates bazelbuild/starlark#20 Change-Id: I03799ea17c1fb3b5658d0b285c28813900783c35
See bazelbuild/starlark#145 for spec changes. Updates bazelbuild/starlark#20 Change-Id: I31e6258cc6caef6bcd3eab57ccec04f1b858b7e7
See bazelbuild/starlark#145 for spec changes. Updates bazelbuild/starlark#20 Change-Id: I31e6258cc6caef6bcd3eab57ccec04f1b858b7e7
See bazelbuild/starlark#145 for spec changes. Updates bazelbuild/starlark#20
The Go implementation has a list of remaining differences from the Java implementation: https://github.com/google/starlark-go/blob/master/doc/spec.md#dialect-differences
I'd like us to finish the wording of a spec that we can all be happy with, even if that spec allows for some differences among implementations. I'll go through the list of differences point by point:
multiprecision integers: the spec should require that integer precision be sufficient to represent uint64 and int64 values without loss, as these are required for correct handling of protocol buffers, among other things. Obviously Bazel has no need for larger integers so it would be fine not to implement it for now, but it should be described as a limitation of the implementation.
floating point: for the same reason, lossless handling and arithmetic on float64 values must also be supported. (On this and the above point I think we were all agreed based on a meeting in NYC about 18 months ago.) Bazel has no need of floating-point at all, so again, we can state that this is a limitation of the Java implementation.
bitwise operators should be supported. They are fundamental operations on integers in every machine and programming language. Bazel may not need them, but many other uses do (anything that uses protocol buffers, for example.)
strings: we cannot realistically require a particular string encoding (UTF-8 or UTF-16) without imposing intolerable costs on implementations whose host language uses the opposite encoding. I propose we specify strings in terms of code units without specifying the encoding; UTF-8 and UTF-16 are only quantitatively different in that sense. However this does leave the Java implementation without a data type capable of representing binary data.
strings should have methods elem_ords, codepoint_ords, and codepoints. I think there was agreement on this point but the Java implementation was lagging.
A language needs some way to encode a Unicode code point as a string (and vice versa). One way to do this is the Go impl's chr and ord built-in functions. (Related: the "%c" formatting operator, which is like "%s" % chr(x).)
The Go impl permits 'x += y' rebindings at top level. I think it should probably match the Bazel implementation (which rejects them), but the whole no-global-reassign feature should be specified as a dialect option, since no client other than Bazel wants it.
The Go implementation treats
assert
as a valid identifier. Indeed, it uses it widely throughout its own tests. The cost of specifying this would be that tools (such as Bazel tests) that use the Python parser will not be able to parse Starlark files that use 'assert' as an identifier. Given that using Python in this way is a hack, and that files containing assert will be vanishingly rare in the Bazel test suite, that doesn't seem like a problem.The Go impl's parser accepts unary + expressions for parity with every other ALGOL-like language. A + operator forces a check that its operand is numeric, and occasionally makes code more readable. I think the spec should include it.
In the Go impl, a method call x.f() may be separated into two steps: y = x.f; y(). I think work is underway to support this in the Java impl too. I recall we were at least agreed it was the right thing.
In the Go impl, dot expressions may appear on the left side of an assignment: x.f = 1. This is a parser issue---in Bazel, there are no mutable struct-like data types for which this operation would succeed, but other applications may need it (esp. if they use protocol buffers), so the grammar should support it nonetheless.
In the Go impl, the hash function accepts operands besides strings, as in Python. It should be an easy fix to the Java implementation to do so too.
The Go impl's
sorted
function accepts the additional parameterskey
andreverse
. These make it easier to define alternative order without the effort and unnecessary allocation of the decorate/sort/undecorate trick and a separate call to reverse.The Go impl's
type(x)
returns "builtin_function_or_method" for built-in functions. This is the string Python uses. I don't have a strong feeling about the particular string, but the crucial thing is that builtin- and Starlark-defined functions must have distinct types because they support different operations. For example, in Bazel, the rule.outputs mechanism requires that its operand be a Starlark function so that its parameter names can be retrieved; this is impossible with a built-in function.The text was updated successfully, but these errors were encountered: