Dart's warnings, errors, and checked and production modes


The Dart team talks about "checked" and "production" mode. Dart's systems can generate warnings and exceptions. I wanted to wrap my head about the two different modes and the two different kinds of feedback, so I wrote this post to gather my thoughts.

Dart uses both warnings and errors to signal detected problems. Dart detects problems both during static compilation (or analysis) and during dynamic execution.

Warnings and Errors

A warning does not halt execution. It seems obvious, but look for the word "warning". That tells you a potential problem has been detected. The program will still be compiled, and, if you're running the Dart VM, will be executed.

An error, on the other hand, throws an execution. If you do not catch the exception, it will halt your program.

Dart detects some type assignment problems during compilation time, if given enough information. For example, the following code uses static types:

num add(num x, num y) => x + y;
add("hello", "world"); // warning: strings aren't numbers

Compiling the above program will issue a warning, because the literal strings "hello" and "world" are not numbers, and the system had enough information to detect this for you.

If you don't give enough type information, the static analysis won't be able to issue type warnings. For example:

add(x, y) => x + y;
add("hello", "world");

The compiler doesn't know that x and y are numbers, so it can't issue a warning.

Remember, static analysis and compilation are different than execution. So far, we've been talking about steps that happen before execution. Give the system enough type information, and the static analysis and compilation steps will warn if you if something might go wrong.

Check and production modes

During execution, Dart programs run in two modes: "checked" mode and "production" mode. In checked mode, dynamic type assertions are turned ON. Given our code sample from above, which generates warnings yet still compiles:

num add(num x, num y) => x + y;
add("hello", "world");

In checked mode, (which you can turn on in the VM and Frog with --enable_type_checks), the type assertions will throw an exception because, dynamically, the types are checked and BOOM you can't pass a String where it expects a number.

In production mode, though, the program runs as if static types were omitted and dynamic type assertions are disabled. In production mode, the above sample will execute to completion, because at the moment you can concatenate two strings with + (WARNING: soon, string + concat will be removed, used only for illustrative purposes).

Why even have a production mode that ignores static types? A core tenet of Dart is that it compiles to JavaScript, which does not have static types. To keep performance high, the Dart program must have the same runtime semantics with or without static types.

Production mode is also useful because the VM needs to compile Dart code quickly. Performing static analysis in the VM at compile time is therefore not always an option and often not sufficient to replace runtime type checking. Runtime type-checking is expensive, especially in presence of type arguments (generics).

Summary

Dart programs EXECUTE in two modes: checked (with dynamic type assertions turned ON) and production (with dynamic type assertions turned OFF).  Dart programs COMPILE with some static analysis capabilities, and will issue WARNINGs if enough type information is given for it to detect potential problems. These warnings do not halt the process, the program will still begin executing.

Next Steps

Read more about optional typing and its implications in an article by Gilad Bracha, spec lead for Dart. Learn more about turning on checked mode in Dart VM and Frog.

Popular posts from this blog

Lists and arrays in Dart

Converting Array to List in Scala

Null-aware operators in Dart