【iOS14】デフォルトブラウザを変更した時にcanOpenURLがfalseになる問題

# 何が起こっている？
iOS14 PublicBeta8以降を入れたiOS端末で、デフォルトブラウザを変更した際にブラウザ遷移が行えない。

# 発生条件
- iOS14PB版、もしくはGM版、正式版(iOS14.0)
    - 2020/09/28追記：iOS14.0.1でも発生することを確認済み
- デフォルトブラウザをsafari以外に設定していること

### デフォルトブラウザ設定方法
1. 「設定」アプリ起動
2. デフォルトブラウザにしたいアプリへ移動(例：Chrome,Microsoft Edge)
3. 「デフォルトブラウザApp」を開く
4. 標準ブラウザをSafariからChromeに変更する

# 原因
UIApplicationの`canOpenURL` メソッドがfalseを返却している。
これが、iOS14の仕様なのかバグなのかは現時点(日本時間2020/09/16)では不明。
[canOpenURL returns false when I changed the default browser on iOS 14](https://developer.apple.com/forums/thread/660241)

# そもそもcanOpenURLとは？
[UIApplication | Apple Developer Documentation](https://developer.apple.com/documentation/uikit/uiapplication)より
>Determine whether there is an installed app registered to handle a URL scheme (canOpenURL(_:))
>(URLスキームを処理するために登録されたインストール済みアプリがあるかどうかを判別する)

アプリから別のアプリを起動する（URLスキーム）際に、処理するためのアプリが端末に存在しているかを返す関数。
（そもそもここの認識が間違えていて、「全てのURL起動にcanOpenURLを通す」という誤用？が今回の事件を引き起こしたと思われる）

# 対応方法
## その１：canOpenURLを通さない
そもそもiOS端末にはブラウザアプリとしてSafariが必ず入っている。
かつ長押ししてもsafariアプリは削除もできないので、
**ブラウザ起動をしようとして、iOS端末にブラウザアプリがないことは有り得ない** はず。
(とはいえ、ブラウザ起動でcanOpenURLがfalseを返すことはないはずが、今回起こっているわけですが)
*2020/09/29追記：コメントにて、構成プロファイルの`allowSafari`でSafariを無効化できると教えていただきました。設定している場合は注意してください。*

上記の通り、canOpenURLの目的は別のアプリの起動ができるかを確認するためのもののため、
ブラウザ起動のためのURL起動の場合は、canOpenURLを通す必要はなさそう。

よっていきなり`open`を叩くように修正する。
これでデフォルトブラウザを変更していても、ちゃんとsafariではないブラウザアプリで起動される。

```Swift
// AS-IS例
if UIApplication.shared.canOpenURL(URL(string: "https://qiita.com/")!) {
      UIApplication.shared.open(URL(string: "https://qiita.com/")!)
} else {
      print("ブラウザ起動失敗")
}
```
```Swift
// To-BE例
UIApplication.shared.open(URL(string: "https://qiita.com/")!)
```


## その２：plistにhttp/httpsを追加する
[Preparing Your App to be the Default Browser or Email Client | Apple Developer Documentation](https://developer.apple.com/documentation/xcode/allowing_apps_and_websites_to_link_to_your_content/preparing_your_app_to_be_the_default_browser_or_email_client)より
>Fulfilling Default Browser Requirements
Apps that register as a default web browser option must satisfy the following criteria:
Your app must specify the HTTP and HTTPS schemes in its Info.plist file.
(デフォルトのブラウザ要件を満たす
デフォルトのWebブラウザオプションとして登録するアプリは、次の条件を満たす必要があります。
アプリは、Info.plistファイルでHTTPおよびHTTPSスキームを指定する必要があります。)

ブラウザ起動のURLを許可するようplistを以下のように変更する。

```
	<key>LSApplicationQueriesSchemes</key>
	<array>
		<string>http</string>
		<string>https</string>
	</array>
```
2020/9/28追記：デフォルトのメールアプリを変更した場合、 mailto:// も同様にcanOpenURLがfalseになりますが、同じくplistに追加で回避可能です。

# 参考
公式： 
[UIApplication | Apple Developer Documentation](https://developer.apple.com/documentation/uikit/uiapplication)
[canOpenURL(_:) | Apple Developer Documentation](https://developer.apple.com/documentation/uikit/uiapplication/1622952-canopenurl)

参考：
[特定のアプリがインストール済みかチェックする](https://qiita.com/star__hoshi/items/f3daa809b36b5f91d653)
[[iOS] ディープリンク（Custom URL Scheme）でアプリを起動する](https://dev.classmethod.jp/articles/ios-custom-url-scheme/)
[iOS9でカスタムURLスキームの遷移に失敗するときの注意点](https://qiita.com/Night___/items/60355d21951cffbef51b)

----
間違っている点や他の方法があれば教えてください！
iOS14の発表でバタバタしている同志のiOSエンジニアのみなさま、お互いに本当にお疲れ様です。


免責：全てのiOS14のアプリの動作を保証する解決方法ではございません