Skip to main content

Highlights from the TC52 meeting on Feb 24, 2015

At the last TC52 meeting on Feb 24, 2015, we discussed a number of additional language features for Dart - including async, tear-offs and null-aware operators.

Update on async

Gilad reported that the implementation had, unsurprisingly, exposed some subtleties in the spec that need to be considered.  Some small adjustments in the language specification may follow from this.

The virtual machine now implements the sync* mechanism.  The async* mechanism is coming along.  The dart2js implementation is complete with respect to the feature set, but it still needs to be debugged.

The development of the async features has given rise to some useful insights.  For instance, sync* creates a synchronous generator, handling all the boilerplate for lazy iteration.  However, the documentation of the library classes need an enhanced level of precision in order for this to work well with the language implementation and specification.  The connection arises because the language specification says that Iterable is implemented by sync* methods.  A conflict arises because Iterator and other classes are allowed to cache some values such as the length, but this is not applicable for sync* functions, and so the spec needs to restrict that.  Consequently, the library documentation has been revised.

An issue arises with “nested” empty iterables for yield*.  The idea is that yield* is used to merge the output from a subiterator into the output of a given iterator.  The wording in the language specification did not specify exactly what to do if that subiterator were empty, but the intention is that the subiterator should be processed normally and iteration should be continued from where it was before that subiterator was inserted.  Adjustments to the specification will be made to clarify this.

Several issues have come up in connection with async primitives:

One issue is whether a construct on the form await (throw x) can throw immediately, or “await always awaits” must prevail.

It was noted that the return type of async uses flatten to avoid nested future types, and also that this should not create any difficulties for the type analysis.

It is not obvious whether await-for loops should require a Stream as the source of the awaited data, or they should allow for non-Stream objects with the required features.  The question arises statically, where a type warning may or may not be given for a non-Stream.  The question arises dynamically where a non-Stream may cause a runtime type error.

Currently, the implementation performs such a check dynamically, even in production mode.  We quickly agreed that it is problematic to have a dynamic check without an accompanying static warning, and also that any such dynamic check should probably only be performed in checked mode.  It is not obvious how to resolve the overall issue, though.

Erik pointed out that there is an underlying principle for this kind of decision:  The language may allow for any object that responds to the requests made by the generated code, or it may enforce a nominal type such that only objects implementing Stream can be used.  The rationale for the former approach (let us call it the “pragmatic” approach) is to run everything that can plausibly be given a semantics, no matter whether or not it is aligned with the associated type structure.  The rationale for the latter approach (let us call it the “typeful” approach) is to support software correctness via explicit contractual obligations and expectations (as expressed by nominal types and supported by dartdoc comments etc.).  It is possible to use both a pragmatic approach and a typeful approach, both statically and dynamically, so all four combinations must be considered.

Dynamically, the pragmatic approach seems to be well aligned with many other decisions in the language design (it’s the “Darty” choice); but as Gilad mentioned, the code that actually implements the features which are used in this context is so subtle that ad-hoc alternative implementations to the ones in the standard library are very likely to be a steady source of stubborn bugs.  For the few highly sophisticated developers who insist on writing their own implementations of “something that works as a stream” it should be easy to add an implements Stream clause to their implementation, such that it works with the stricter, typeful approach.

Statically, the pragmatic approach may be seen as a mistake, especially in the (presumably, vast majority of) cases where a non-Stream is used by accident rather than by intention.  Conversely, if a static warning is given whenever a non-Stream is used in this context, it will cause frustration for the sophisticated developers who have carefully chosen to use a non-Stream.

In summary, we may have implicitly preferred the typeful approach statically and the pragmatic approach dynamically, but no explicit decision was made.

Another matter is that a decision on an underlying principle in this case naturally affects the treatment of similar constructs, including the standard for statement, where changes would obviously be much more difficult.

A quite different issue is the decision about whether yield in async* may suspend.  If a tight loop contains a yield, it may produce a large number of data items which are not being received quickly enough.  These situations create a need for more flexibility than that which is currently granted by the specification.

Finally, Gilad mentioned that there are some missing static warnings in relation to async*/sync*, and a few other small issues.

Update on “Dart Enhancement Proposal”

We are ready to launch the process, and several activities are already taking place.  The process is github-based (see  The idea is that DEP authors file an issue in this github repository which includes a link to the proposal itself, which is stored as a separate github repository.  The proposal repository may also contain other elements such as examples, implementation etc.  The committee will go over incoming proposals according to the flowchart.

TC52 has a royalty-free patent policy. Therefore, when a proposal is accepted by the DEP committee for processing by TC52, the original contributor of the DEP needs to sign the 'ECMA TC52 external contributor form'.

Update on language extensions

Two things are likely to be ready for the next version of the language specification: Generalized tear-offs, and null-aware operators.

For generalized tear-offs, the coverage and discussions at the previous meeting are still valid.  Now there is a complete proposal which is currently getting prepared for markdown presentation etc.  It can be found at  It is done in a way that should be identical to the way that an external contributor could submit a proposal, such that it also serves as a test of the procedure and the associated documents.

For null-aware operators, the information and discussions from the previous meeting are still valid.  In this case it is a very simple proposal, just syntactic sugar, but it comes at a low cost.

We briefly discussed a proposal from Erik to change the class Function to take one type argument which would be the return type of the function represented by the given instance.  This could enable the type Function<T> to be more useful than the current type Function, and it seems to be a benign change because all existing occurrences of Function would be reinterpreted to mean Function<dynamic>, which would have a backward compatible semantics.

We did not discuss configurable imports, union types, generic methods, closure tear-offs, improvements to Type Promotion, nor subtyping for function types.  In most cases this was because there is nothing new.  For function type subtyping it was because we need to consider changes to the runtime semantics of Dart very, very carefully before we commit to them.

Next meeting

The next TC52 meeting is on March 19th, 2015. Main topics expected are finalization of tear-offs and null-aware operators.

Popular posts from this blog

A stronger Dart for everyone

We are constantly asking ourselves:
How do we make developers even more productive when writing Dart apps? We believe that a critical part of the answer to this question is to make strongmode – a sound static type system for Dart – the standard for all Dart developers.

Teams that use Dart to build apps like Soundtrap, AdWords, AdSense, and Greentea say they really enjoy using strong mode features, such as early error detection. In fact, teams that have switched completely to strong mode cite not only early error detection but also better code readability and maintainability as major benefits. We hear this both from small teams and Рeven more so Рfrom large teams with hundreds of developers writing and maintaining millions of lines of Dart code. As Björn Sperber from Soundtrap says,
Strong mode and the smooth integration with IntelliJ is a joy to use and a huge improvement. If you’ve tried out Flutter, you’ve already used strong mode checks from the Dart analyzer.

Given the benefits …

AngularDart 3.0: Easy upgrade, better performance

AngularDart 3.0 is now available. It brings better performance and smaller generated code, while also making you more productive.

Version 3.0 is an evolution: although it has some breaking changes (detailed below), it is a smooth upgrade due to minimal public API adjustments. Most of the progress is under the hood—in code quality, stability, generated code size, performance, and developer experience.

Code quality:
2731 instances of making the framework code more type safe (using sound Dart).The AngularDart framework code size is down by 12%.Many additional style updates to the codebase:Changed to use idiomatic <T> for generic methods.Removed NgZoneImpl, all the code exists in NgZone now.Stability:
Many CSS encapsulation fixes due to update with csslib package.Fixed bugs with IE11.

For the Mail sample app, we see 30% faster time-to-interactive (currently 3812 ms on a simulated 3G connection, measured via Lighthouse).Our large app benchmark shows 2x faster render times of…

Dart 1.24: Faster edit-refresh cycle on the web & new function type syntax

Dart 1.24 is now available. It includes the Dart Development Compiler and supports a new generic function type syntax. Get it now!

Figure 1: DDC debugging in Chrome.

Some notable changes in this release:
pub serve now has support for the Dart Development Compiler. Unlike dart2js, this new compiler is modular, which allows pub to do incremental re-builds for pub serve.In practice what that means is you can edit your Dart files, refresh in Chrome (or other supported browsers), and see your edits almost immediately. This is because pub is only recompiling your package, not all packages that you depend on.There is one caveat with the new compiler, which is that your package and your dependencies must all be strong mode clean.You can also use the new compiler to run your tests in Chrome much more quickly than you can with dart2js.Read more in the changelog.You can now publish packages that depend on the Flutter SDK to pub. Moreover, has started tagging Flutter plugins with …