Slide 1

Slide 1 text

© 2023 Wantedly, Inc. 個人開発アプリでの Swift Macros 紹介 Mobile勉強会 Wantedly × チームラボ #11 Oct. 17 2023 - 林達也

Slide 2

Slide 2 text

自己紹介 © 2023 Wantedly, Inc.

Slide 3

Slide 3 text

Agenda 1. Swift Macros とは 2. 開発中のアプリでの利用例 ○ member ○ peer ○ accessor 3. 使ってみた感想 © 2023 Wantedly, Inc.

Slide 4

Slide 4 text

Swift Macros とは © 2023 Wantedly, Inc.

Slide 5

Slide 5 text

Swift Macros ● ソースコードのコンパイル時にコードを変換し、繰り返し書く手 間を省く ● Swift では 2 種類のマクロがある ○ Freestanding macros ■ 引数のみに依存して独立して展開される ■ #function, #warning ○ Attached macros ■ 宣言に付属して対象の情報を利用して展開される ■ @Observation © 2023 Wantedly, Inc. https://docs.swift.org/swift-book/documentation/the-swift- programming-language/macros/

Slide 6

Slide 6 text

Swift Macros ● ソースコードのコンパイル時にコードを変換し、繰り返し書く手 間を省く ● Swift では 2 種類のマクロがある ○ Freestanding macros ■ 引数のみに依存して独立して展開される ■ #function, #warning ○ Attached macros ■ 宣言に付属して対象の情報を利用して展開される ■ @Observation © 2023 Wantedly, Inc. https://docs.swift.org/swift-book/documentation/the-swift- programming-language/macros/

Slide 7

Slide 7 text

アプリの紹介 © 2023 Wantedly, Inc.

Slide 8

Slide 8 text

開発中のアプリの紹介 ● Swift 5.9, iOS17 SDK の機能 を色々試してみる環境 ● Apple のドキュメントブラウザア プリ © 2023 Wantedly, Inc. https://github.com/swiftty/apple-documentation

Slide 9

Slide 9 text

public init © 2023 Wantedly, Inc.

Slide 10

Slide 10 text

public init ● ドキュメントデータの構造の数だ け型を用意 ● マルチモジュール構成で開発し ているため public init が 全てに必要… ○ Macro で楽をしたい © 2023 Wantedly, Inc.

Slide 11

Slide 11 text

@attached(member) ● member ○ 型に対してアタッチすることができる Macro ○ 引数の declaration からプロパティなどのメンバー情報を取得 ● →プロパティ定義を収集して init を生成 © 2023 Wantedly, Inc.

Slide 12

Slide 12 text

ImplicitInitMacro ● members: MemberBlockItemListSyntax から 各プロパティの名前、型、初期値を取り出す © 2023 Wantedly, Inc.

Slide 13

Slide 13 text

ImplicitInitMacro ● variables から引数リストを構築 ○ init(FunctionParameterListSyntax) ○ foo: Foo? = nil を組み立て © 2023 Wantedly, Inc.

Slide 14

Slide 14 text

ImplicitInitMacro ● init を構築 ○ init() { for-loop } ○ self.foo = foo を組み立て © 2023 Wantedly, Inc.

Slide 15

Slide 15 text

EnvironmentKey © 2023 Wantedly, Inc.

Slide 16

Slide 16 text

EnvironmentKey ● SwiftUI の EnvironmentKey を定義する際に定型文が頻 発 © 2023 Wantedly, Inc.

Slide 17

Slide 17 text

EnvironmentKey ● SwiftUI の EnvironmentKey を定義する際に定型文が頻 発 © 2023 Wantedly, Inc. このように書きたい

Slide 18

Slide 18 text

@attached(peer), @attached(accessor) ● peer ○ 任意の宣言と並べて新たな定義を用意できる Macro ■ @AddAsync のようにメソッドを追加させたいときなど ● accessor ○ プロパティの getter, setter を生成できる Macro © 2023 Wantedly, Inc.

Slide 19

Slide 19 text

SwiftUIEnvironmentMacro ● peer マクロで EnvironmentKey に適合する型を生成 ○ 返却する Syntax は ExpressibleByStringInterpolation に 適合しているので文字列で実装することも可能 © 2023 Wantedly, Inc.

Slide 20

Slide 20 text

SwiftUIEnvironmentMacro ● accessor マクロも同様に getter と setter の Syntax を 生成 ○ peer で生成される型を参照 © 2023 Wantedly, Inc.

Slide 21

Slide 21 text

Tips © 2023 Wantedly, Inc.

Slide 22

Slide 22 text

Tips ● Swift AST Explorer がやっぱり便利 ○ https://swift-ast-explorer.com/ ○ どこでどの Syntax が現れるかを確認し て、キャストするため ● SwiftSyntaxMacrosTestSupport の assertMacroExpansion も期待 する生成結果かどうか確認しやすい © 2023 Wantedly, Inc.

Slide 23

Slide 23 text

感想 ● ボイラープレートで煩雑に感じていたコードがマクロでスッキ リするのは良い体験 ● resultBuilder や ExpressibleByStringInterpolation のサポートで直感的に追加するコードを書ける ● dependency に swift-syntax が必要 ○ 3rd party の Macro ライブラリだと微妙にニーズが満たせなかった り swift-syntax によって依存関係がシビアになりがちなので、しば らく自作が良さそう © 2023 Wantedly, Inc.