Xcode8 – Swift3への変換MEMO (1)

広告:超オススメUnity Asset
  広告:超オススメUnity Asset

寝落ちして朝目覚めたらXcode7がXcode8になっていたことで、全プロジェクトをSwift3へ移行し始めることにしました。毎度のことですが、新しいバージョンのSwiftにConvert(コンバート/変換)を行うと、あらゆる箇所でエラーが発生します。

(このコンバート作業に関する内容は、今後も「Swift2to3タグ」をつけてMEMOしておこうと思います。)

もし、不本意ながらXcode8にしてしまった後、Xcode7を共存させたいと思った場合は、こちらから古いバージョンをダウンロードして、リネームすることで共存させることができるようです。(試していませんが)

Swift2to3

コンバートを開始する前に、そのプロジェクト全体をGit管理して、変換前の状態をコミットし、いつでもその変換前の状態に戻せるようにしておくのがいいと思います。(ソースの管理にはBitBucketを使っています。)

Swift3へのコンバートは、まず自動でXcodeにやらせました。その後、大量に出たエラーをひとつずつ潰していくというパターンです。ほとんどXcodeに提案されるがままに処理していきました。ビルドできるようになってから、動かなくなった箇所をちょっとずつ調査するという流れです。

どうしても解決しない箇所は、とりあえず「//swift3」とか目印をつけておいて、その箇所全体をコメントアウトしてでもエラーをなくしておきます。

Swift製の他力フレームワークは外しました

今回痛感したのは、CocoaPodsで組み込んだモジュールのうち、Swift製のものが最新版でもまだSwift3対応していない(場合が多い)という点でした。Swiftがもう少し落ち着くまでは、Objective-Cベースのものにしておくのがいいかもですね。

TableViewControllerに必要なメソッドは自動的に変換してくれなかった

Swift3では、

func tableView(tableView : ...)

func tableView(_ tableView : ...)

のような形に変更されたことで、この変換作業が大量に生じると思います。この「_」がどのような意味を持つのか、についての詳細は大重さんの本を待つとして、とにかく「_」をつけておかねばならないメソッドがたくさん見つかるので手作業で修正していきます。そうした中で、TableViewControllerに必要な「numberOfRowsInSection」や「cellForRowAt」など頻繁に使うものも、記述がだいぶ変更され、しかも自動的に変換もできなかったりしたので、これらについては、相対するSwift3での記述を、コードヒントを頼りに手書きで書き換えていきました。(一度、メソッド部分を消して、「number・・」と書き込んでコードヒントの中から候補を選択した方が確実ですね)

AppDelegateのdidFinishLaunchingWithOptionsがprivateに変換された

TableViewControllerなどと同様にAppDelegate内のメソッドも変換が必要です。が、Xcodeからの提案される変換候補が正しくないことがありました(正常に行く場合もあるのかも)。Xcodeの言う通りに処理をすると「private」をつけるだけ、だったりしました。ここまで重要でどのアプリにもあるものなんかは、正しく変換してほしかった。

 これ、privateであっても、エラーではなくなるので、そのままビルドも実行もできるようになります。が、ここでの初期化が行われなくなります。「swift3にしたら、なんか初期化が行われなくなった」みたいな現象を感じたら、これかもです。

この部分だけ、手書きで変換する様子をキャプチャしておきましたので、ご参考までに。

AppDelegateのdidFinishLaunchingWithOptionsがprivateに変換された from mushikago on Vimeo.

他にもいろいろと変換作業で気がついた点などは、今後もMEMOを残していこうと思います。