Dart 1.19リリースノート 


Dart 1.19がリリースされました。今回のStrong Mode周りの変更などはなかなか便利なので紹介していきます。

# 関連リンク

- 開発ブログ : [Dart News & Updates: Dart 1.19: Improved developer experiences](http://news.dartlang.org/2016/08/dart-119-improved-developer-experiences.html)
- CHANGELOG : [sdk/CHANGELOG.md at master · dart-lang/sdk](https://github.com/dart-lang/sdk/blob/master/CHANGELOG.md#1190)

# 1.19 変更点

## 言語仕様の変更

### 最後の引数やパラーメータにカンマをつけることが可能に

関数宣言における最後のパラメーターや関数呼び出しにおける最後の引数のあとにtrailing commaをつけることが可能になりました。開発が楽になりますね。


```dart
void main() {
  var test = new TestClass(
    str1:"A",
    str2:"B",
    str3:"C",
    str4:"D", // この行の最後のカンマがつけられるようになった
   );
  test.func2(); // ABCD
}

class TestClass {
  String str1,str2,str3,str4;
  
	TestClass({
        this.str1,
        this.str2,
        this.str3,
        this.str4, // この行もOK!
     });
	void func2(){
  	print(str1 + str2 + str3 + str4);
	}
}
```

これは開発ブログに表示されていたgifを見るとさらにわかりやすいと思います。

![img](https://2.bp.blogspot.com/-kVBJlnXby54/V8DJqaZsvwI/AAAAAAAANeU/suPDhaZcdsEvN1DuYy8669JJ-W6x1zX1wCLcB/s1600/ReorderCode.gif)

> 画像元: [Dart News & Updates: Dart 1.19: Improved developer experiences](http://news.dartlang.org/2016/08/dart-119-improved-developer-experiences.html)

関連Issue : [Allow trailing commas in parameter and argument lists. · Issue #26644 · dart-lang/sdk](https://github.com/dart-lang/sdk/issues/26644)


## 周辺ツールの変更点

### dartfmt

上の言語仕様の変更にともなってtralling commas関連のフォーマットをサポートしました。そのほかにも改善されたようです。詳しくは[dart_styleレポジトリのCHANGELOG](https://github.com/dart-lang/dart_style/blob/master/CHANGELOG.md)を確認してください。

### Pub

主要な変更を取り上げていきます。その他はCHANGELOGを確認してください。

- `--no-packages-dir`フラグが`pub get`、`pub upgrade`、`pub downgrade`に追加されました。このフラグをつけてコマンドを実行すると、pubは`packages/`をせず、またもしある場合も削除してくれます。これは`--no-package-symlinks`フラグがサポートされなくなったものを埋め合わせるためのものです。
- Flutter SDKのバージョンをpubspec.yamlの中で指定できるようになりました。

  ```yaml:pubspec.yaml
environment:
  flutter: ^0.1.2
  sdk: >=1.19.0 <2.0.0
```

- packageの`dependencies`を指定する際に、sdkからそのpackageを取得するためのオプション`sdk`が追加されました。現在はflutterだけサポートされています。上の変更と合わせてflutter関連のためのようですね。

  ```yaml:pubspec.yaml
dependencies:
  flutter_driver:
    sdk: flutter
    version: ^0.0.1
```
  関連Issue
  * [SDK dependencies · Issue #1431 · dart-lang/pub](https://github.com/dart-lang/pub/issues/1431)
  * [Flutter SDK constraint · Issue #1432 · dart-lang/pub](https://github.com/dart-lang/pub/issues/1432)


### dart2js

   - `dart2dart`( = `dart --output-type=dart`)が削除されました。1.11からdeprecated だったのでそこまで影響はないと考えられます。

## DartVMについて

DartVMをビルドするために、C++11をサポートするコンパイラが必要になりました。古いバージョンのLinuxディストリビューションを利用している場合は注意が必要です。GCC4.8以上が必要とのことです。clangやXCodeで使われているコンパイラでは問題なく動くことが確認されています。

参考 : [Building · dart-lang/sdk Wiki](https://github.com/dart-lang/sdk/wiki/Building)

## Strong Mode

AnalyzerのStrong Modeがさらに強力になりました。追加された機能を見てみましょう。

### 新機能

#### Disable implicit casts

これは名前のとおり暗黙のダウンキャストを許可しないオプションです。ダウンキャストとは、基底クラスから派生クラスへの型変換を指します。下のサンプルコードを確認してみてください[^1]。

```dart
void main(){
  Base test = new Base();
  Sub test2 = test; // disable implicit castsを有効にするとここでerrorに
  print(test2.str2); // こういうエラーを事前に検知できる
}

class Base {
    String str;
}
class Sub extends Base {
    String str2;
}
```

使いたい場合は.analysis_optionsで指定するか、

```yaml:.analysis_options
analyzer:
  strong-mode:
    implicit-casts: false
```

もしくはdartanalyzerで--no-implicit-casts を指定してください。

```
dartanalyzer --strong --no-implicit-casts ~.dart
```

[^1]:[公式ドキュメント](https://github.com/dart-lang/dev_compiler/blob/master/doc/STATIC_SAFETY.md#disable-implicit-casts)もありますが、すこしサンプルがわかりづらかったのでこういう形にしました。

#### Disable implicit dynamic

これは暗黙のdynamicを禁止するものです。[ドキュメント](https://github.com/dart-lang/dev_compiler/blob/master/doc/STATIC_SAFETY.md#disable-implicit-dynamic)にのっているサンプルコードがわかりやすいです。

```dart
main() {
  var x; // これはエラー
  var i = 123; // これはintと推論できるのでOK
  dynamic y; // これはdynamicで宣言しているのでOK!
}
```

ドキュメントに
> This also affects: parameters, return types, fields, creating objects with generic type, generic functions/methods, and supertypes

とあるように、これは多くの場所で作用します。

```dart
// これもエラーになります。
f(x) => x + 42;
dynamic f(dynamic x) => x + 42; //OK!
int f(int x) => x + 42; // okay

// クラス内のメンバー変数にも作用
class C {
  var f; // これはエラー
  dynamic f; // OK!
}

main() {
  var x = []; // 暗黙で List<dynamic> になっているのでだめ
  var y = [42]; // OK!: List<int>
  var z = <dynamic>[]; // OK!: List<dynamic>

  T genericFn<T>() => null;
  genericFn(); // 暗黙で genericFn<dynamic> になっているのでだめ
  genericFn<dynamic>(); // OK
  int x = genericFn(); // OK:  暗黙の genericFn<int>だということがわかる
}

// エラー
class C extends Iterable { /* ... */ }
// OK
class C extends Iterable<dynamic> { /* ... */ }
```

使いたい場合は.analysis_optionsで指定するか、

```yaml:.analysis_options
analyzer:
  strong-mode:
    implicit-casts: false
```
 
 もしくはdartanalyzerで`--no-implicit-dynamic`を指定してください。

```
dartanalyzer --strong --no-implicit-dynamic *.dart
```
 

上2つの機能はどちらも開発中のものです。フィードバック募集中とのことでもありますし、便利ですので使ってみてはいかがでしょうか。


### Breaking Chanages

- コンストラクタを呼び出すときの変数から推論をしてくれるようになりました。

  ```dart
var map = new Map<String, String>();
  
// infer: Map<String, String>
var otherMap = new Map.from(map);
```
 関連Issue : [infer constructor type arguments from values · Issue #25220 · dart-lang/sdk](https://github.com/dart-lang/sdk/issues/25220)

- ローカル関数の返り値を推論してくれるようになりました。

```dart
void main() {
  // 返り値はintだと推論してくれる
  f() { return 40; }
  int y = f() + 2; // 型チェック
  print(y);
}
```

関連Issue : [infer local function return types · Issue #26414 · dart-lang/sdk](https://github.com/dart-lang/sdk/issues/26414)

- ジェネリック型のパラーメーターにおけるtype promotionを許可するようになりました。

```dart
void fn/*<T>*/(/*=T*/ object) {
  if (object is String) {
    // `object`はこのblockの中では`String`として扱われる
    print(object.substring(1));
  }
}
```

関連Issue : ["is" checks aren't considered with generic-method types · Issue #26965 · dart-lang/sdk](https://github.com/dart-lang/sdk/issues/26965)

- `Future.then`に関する推論が賢くなりました。`.then/*<Future<SomeType>>*/`が必要なくなりそうです。

```dart
// これも推論してくれる
Future<List<int>> t2 = f.then((_) => [3]);
// これもOK.
Future<int> t2 = f.then((_) => new Future.value(42));
```

関連Issue: [Can strong mode inference for Future.then be improved? · Issue #25944 · dart-lang/sdk](https://github.com/dart-lang/sdk/issues/25944)

- async 関数に関する推論も賢くなりました。

```dart
void test() async {
  List<int> x = await [4]; // これは今までも推論してくれていた
  List<int> y = await new Future.value([4]); // 今はこっちも推論してくれる
}
```
関連Issue : [Handle implicit future unions in downwards inference · Issue #25322 · dart-lang/sdk](https://github.com/dart-lang/sdk/issues/25322)

- Sideway castsが禁止されました。

関連Issue : [Sideways casts should be disallowed · Issue #26120 · dart-lang/sdk](https://github.com/dart-lang/sdk/issues/26120)

もろもろの変更を見ても、かなり快適にStrong Modeの恩恵をうけることができるようになっている印象を受けます。よい。

# あとがき

一時期消えたなどと言われていたDartですが、ここのところはFlutterやAngular2、Googleの新OS「Fuchsia」への採用などのニュースで活気づいています。Dart 2.0のリリースなどもふくめて、Dart Summit 2016までいろいろな動きがありそうです。興味深いものがあったらまとめて行きたいと思います。