2017年夏、Apple ATS対応における試行錯誤

ATS(App Transport Security)*1対応にかんして、あれこれ試してみた結果を備忘的に残しておこうという記事です。
なんか延期とか言われてますけどね…
ATSの概要と詳細については以下:
[iOS 9] iOS 9 で追加された App Transport Security の概要 | Developers.IO

TL;DR

やりたいこと
  • 新規アプリで、不特定多数(含 http)のサイトのOGPを表示したい
  • タップで Safari に遷移

これだけ?ええ、これだけです。これだけなんですけど…。

結論

Cocoa Keys/App Store Review for ATS にあるように、
今回のケースは(きっと)

Must connect to a server managed by another entity that does not support secure connections

に該当するはずなので、 NSAllowsArbitraryLoads を立ててレビューをゴリ押しする…のがよさそうですね。

ただ一度は全展開がアナウンスされた機能ですし、レビューで蹴られるポイントを増やすのもなー、ということで、Azure Functionsでさくっとプロキシさせることに*2しました。PaaS最高。
ただこれ、どう考えてもAppleの思惑からは大きくずれているんですよねえ…。

試したこと

↑の結論に至るまでに、なんとかハックしてやろうといろいろやってみた失敗談。

表示したいものは主に以下の3つ。

  • og:title
  • og:description
  • og:image
ライブラリを使う

GitHub - marty-suzuki/URLEmbeddedView: URLEmbeddedView automatically caches the object that is confirmed the Open Graph Protocol.
当たり前ながらATS対応へのハックはなく、加えて見た目のカスタマイズがちょっと大変そうだったのでお見送り。

NSAllowsArbitraryLoadsInWebContent を立てて WKWebView でロード、metaタグを抜き出して描画

新規アプリだし、いったん iOS10 以降サポートと割り切って突破できないかと考えたんです。
具体的には、

  • WKWebView を作って(addSubView はせず)web ページをロード
  • didFinish のタイミングで evaluateJavaScript を叩いて head を取得、Kanna でパース、表示

これで og:title, og:description, og:image(のURL取得) まではできました、が、http な画像読み込みでまた同じ問題が発生…。*3

そんなら、js側で画像を読み込んで base64 encode してどうにか渡せればいけるのでは…?と、WKUserScript(WebViewとアプリで message のやりとりが可能)で画像を取ってきて canvas に置いて base64 encode して postMessage して…とやってみたら、CORSに引っかかって\(^o^)/オワタ*4



というわけで、こりゃもう八方塞がりですねということで、プロキシサーバに逃げたのでした。
わりと現状は NSAllowsArbitraryLoads 一択という話しか聞かないので、もしいい方法があれば教えてほしいです。

*1:iOS App からwebページを表示させる際に、httpなサイトやAppleの定めた基準を下回るものは弾かれるようになる設定

*2:今回はAPIサーバをAzure Functionsで用意していることもあり

*3:薄々気づいてた

*4:薄々気づいてたよ!!