WWDC15 参加レポート Day4 SwiftとUITestingとThe Bash編
大島 雅人
こんにちは、大島です。
6/8から1週間WWDC15に参加してきました。3日目のレポートから1週間以上空いてしまいましたがなんとか最終日まで書ききりたいと思っています!部屋とYシャツと私みたいなタイトルになってしまいましたが、今回はWWDC4日目のSwiftのセッションとUI Testingについてラボに行ってきた話、WWDCの目玉イベントであるThe Bashの様子をレポートしていきたいと思います。
前回までの記事はこちら
- WWDC15 参加レポート Day0 出発までの準備編
- WWDC15 参加レポート Day1 Keynote徹夜編
- WWDC15 参加レポート Day2 ラボに行ってみた編
- WWDC15 参加レポート Day3 GitHubに行ってきた編
Optimizing Swift Performance
この日朝一で見たセッションです。本セッションはSwiftのコンパイラーの最適化の話です。ここでもStructの話題が出てきておりSwiftにおいてStructはとても重要な概念だなと感じています。セッションの概要は以下の話です。Swiftにfinal
識別子は昔からあったようですが私はお恥ずかしながら今回初耳でした。
- Objective-Cに比べてSwiftの実行速度は数倍速い
- Build Settingsで
Whole Module Optimization
という最適化レベルが選べるようになる - ClassだとReference Countのincrementとdecrement処理が入るのでオーバーヘッドがある
- Genericsはコンパイラによって最適化される
final
とprivate
をつけると動的ディスパッチがなくなるので最適化される- Instrumentsで処理落ちしているところを見つける
昼
日本食が恋しくなり、堂島庵というところに行きました。店内の写真を見て思わずカツ丼を頼んでしまうあたり日本人ですね。米もパサパサしたタイプじゃなく日本のモチモチしたタイプの米でした。やはり日本の米は最高です。
Swift in Practice
まずは、コンパイル時にAPIのdeprecatedチェックできるようになったという話です。今まではObjective-CでもSwiftでもOSのバージョン番号やクラスやメソッドに反応するかどうかを見て処理を分けていました。また、コンパイル時にはdeprecatedかどうかは判断できず実行時にしか確認できませんでした。Swift2.0からはそれをコンパイラーがチェックしてくれるという大きな改善が入りました。一方で、引き続きObjective-Cからはこの構文は使えないのでSwiftを使わないとデメリットになるという一つの材料になってきます。
// OSバージョンチェックのためのavailable構文
if #available(iOS 9.0, *) {
// iOS9.0以上のみのAPI呼び出し
}
// クラスへのアノテーション
@avaiable (iOS 8.0, *)
class Hoge {
// メソッドへのアノテーション
@avaiable (iOS 8.0, *)
func hoge() {}
}
avaiable
の話のあとは、UIImage
やStoryboardなどを生成する際に指定する文字列についての話です。文字列、つまりStringで指定するということはリソースが存在するかは最終的には実行時にしか判断できません。文字列定数と宣言してもよいですが間違えて同じ文字列を指定することもできてしまいます。
まずはUIImageを例に、UIImage(named:)
の引数が文字列なので間違えてしまうかもしれない点、返り値の型がOptional
(つまり失敗する可能性がある)なUIImage?
なので毎回アンラップしなければならない点を問題として説明が始まり、解決法としてEnumとClass Extensionを利用してコンパイラにチェックをしてもらいつつ便利にリソースを呼び出せるテクニックを紹介してくれています。
次は、StoryboardSegueのIdentifierについてのテクニックです。UIImageのときと同様に、SegueのIdentifierをEnumで定義できますがSegueに関してはあるUIViewControllerにしかひもづいていないので、Class Extensionにしてしまうと関係ないSegueも対象に含まれてしまいます。そこで、Swift2.0から使えるProtocol ExtensionとProtocol ExtensionでのWhere句での制約のテクニックを使ったものが紹介されています。このセッションもSwiftっぽく書くためにオススメのセッションです!
UI Testingラボ
質問を待っていると・・
ラボは受付の人に質問したいことを伝えて、受付の人が質問に適したエンジニアをアサインしてくれるシステムになっています。15:30ぐらいに入ってUI Testingの質問があると伝えると、今質問している人が終わるまでこのテーブルで待っててねと言われます。テーブルは円卓なのでAppleエンジニアの周りに人が座る形式です。で、この前の人がすごく長くて30分ぐらい待ちました。やっと自分の番だと思って大人しく待っていたら、あとからきた近くに座っていた方の順番になってしまい、さらに友達みたいな人がきてHey!!一緒に聞かせてよ!みたいな感じになり、Appleエンジニアの方もOK!カモン!みたいな感じでさらに待つことになってしまいました。。
これはやばいと思いなんとかアイコンタクトを送りまくってやっと気づいてもらい、話を聞いてもらうことができました!日本みたいにお行儀よくしててもダメで、積極性が必要ということを感じました。
質問の内容
質問をするために以下のようなコードを用意しました。ログイン画面でログインするとマイページが表示されるという簡単なアプリを作り、それに対してUITestingを書きました。
func testExample() {
// Use recording to get started writing UI tests.
// Use XCTAssert and related functions to verify your tests produce the correct results.
let app = XCUIApplication()
let indicator = app.activityIndicators["Progress halted"]
XCTAssertEqual(indicator.exists, true)
// Question1: How to assert is XCUIElement hidden?
// XCTAssertEqual(indicator.hidden, true)
let idTextField = app.textFields["ID"]
idTextField.tap()
idTextField.typeText("user")
let xcuiSecureTextField = app.textFields["_XCUI:Secure"]
xcuiSecureTextField.tap()
xcuiSecureTextField.typeText("password")
app.buttons["Login"].tap()
// after login
let label = app.staticTexts["This is MyPage"] // MyPageViewController's label
// Question2: How to assert after the asynchronous operation?
XCTAssertEqual(label.exists, true)
}
質問は2つ用意しました。今回はコードに質問を書いたのでかなりすんなりとこちらの意図が伝わりました!英語が苦手な方はこの方法がいいと思います。
- Q1: viewのhiddenはassertできるのか?
- A: できない。要望が多くあればhiddenのプロパティも追加されるかもしれないね。
- Q2: 待ちが発生するような非同期処理はどう対応するのか?
- A: デフォルトで3秒間までリトライをする。3秒以上はwait処理が必要。
The Bash
WWDCでは木曜日の夜はイェルバ・ブエナ・ガーデンズという近くの公園でThe Bashというライブ+お酒+食事の野外パーティーがあります。今年も去年と同じ場所で開催されたようです。会場に行く際はクロークはないから荷物は置いてきてねというお知らせがあり、来年行く方はそのあたりも考慮してタイムスケジュールを組むといいかもしれません。
ライブの様子。あまりはしゃがないところがGeekっぽくていいですよね。
結構外国の方も話しかけてきてくれて基本的にどんなプロダクト作ってるのかみたいな話をしていました。給料はいくらぐらいもらってるのというゲスい話もしたり楽しめました(笑)。ライブが終わったあとはいつのまにか日本人街みたいな集まりもできて楽しく過ごすことがができました!