Xcodeで本番アプリと開発アプリをわけるベストプラクティス

# はじめに
Xcodeでアプリを作る際、本番用アプリだけでなく開発用アプリも作ることがよくあると思います。
Xcodeでアプリをわける方法について記載します。（実際にこうやってるのを見たという紹介です）

# 開発環境
Xcode 10.2.1

Swift 5.0

# 要件
下記のような要件で本番、開発、ダミーの3つのアプリにわけます。

1. 本番、開発、ダミーで別々のアプリにわけたい（bundle idをわけたい）
2. 本番、開発、ダミーで接続先サーバをわけたい
3. 本番、開発、ダミーでアプリ名をわけたい
4. 本番、開発、ダミーでアプリアイコンをわけたい

※ 2.は本番→本番用サーバ、開発→開発用サーバ、ダミー→サーバ接続せずローカルのファイルを読み込むのような想定です。

完成図

<img width="339" alt="t_app" src="https://user-images.githubusercontent.com/34936885/64613507-404f9280-d411-11e9-850d-b83caac77b8a.png">


# 方法
[「やめて...」](#やめて)[「べつにいいけど...」](#べつにいいけど)[「おすすめ」](#おすすめ)の3つの方法を記載します。おすすめは[最後](#おすすめ)のわけ方です。

## やめて...
1つ目はGitのブランチでわける方法です。

Xcodeでわける方法といいつつこれはXcodeの機能を使いません。

### 手順
1. gitのブランチをmaster(本番)、develop（開発）、dummy（ダミー）の3つにわける
2. それぞれのブランチでbundle idを設定する
3. それぞれのブランチで接続先サーバを設定する
4. それぞれのブランチでアプリ名を設定する
5. それぞれのブランチでアプリアイコンを設定する  

これで要件通り3つのアプリにわけることができました！！簡単ですね！！

### 評価
この方法はやめて...

いったいだれがそのブランチを管理するんだい？？今後環境が増えたらその都度ブランチを増やすのかい？？

## べつにいいけど...
2つ目はXcodeのTargetでわける方法です。

### 手順
1. General→TARGETS→Duplicateでターゲットを複製する  
<img width="321" alt="t_dup" src="https://user-images.githubusercontent.com/34936885/64613760-e7342e80-d411-11e9-8762-1d53ac958690.png">
2. 複製したtargetの名称を変更する（PiyoApp copy→PiyoAppDev）
3. 複製されたInfo.plistの名称を変更する（PiyoApp copy-Info.plist→InfoDev.plist）
4. General→Identityで複製したtargetのInfo.plist（InfoDev.plist）を選択する  
<img width="662" alt="t_info" src="https://user-images.githubusercontent.com/34936885/64613723-d2579b00-d411-11e9-8fd7-9e34da62b3fa.png">
5. Generalからbundle idを変更する
6. Generalからアプリ名を変更する
7. Generalからアプリアイコンを変更する
8. Manage Schemes...でスキーム名を変更する（PiyoApp copy→PiyoAppDev）  
<img width="415" alt="t_manage_scheme" src="https://user-images.githubusercontent.com/34936885/64613687-b9e78080-d411-11e9-8540-89c1a56aef66.png">
<img width="770" alt="t_scheme" src="https://user-images.githubusercontent.com/34936885/64613640-9ae8ee80-d411-11e9-91f8-e7d9975deb71.png">
9. Build Settings→Swift Compiler - Custom Flagsにフラグを追加する（開発ならDEVELOPダミーならDUMMYなど）  
<img width="722" alt="t_flag" src="https://user-images.githubusercontent.com/34936885/64613604-81e03d80-d411-11e9-99c4-6ced8c982f3c.png">
10. Dummyも同じように作成する
11. それぞれの環境のサーバの接続先をコードで設定する  

```swift
var serverURL: String {
        #if DEVELOP
        // 開発用URL
        return "https://example.com/piyoDev"
        #elseif DUMMY
        // ダミー用URL(ダミーはローカルのJSONファイル読み込む想定なので空文字でもOK)
        return "https://example.com/piyoDummy"
        #else
        // 本番用URL
        return "https://example.com/piyo"
        #endif
    }
```
 
多少手間がかかりましたがこれで要件通り3つのアプリにわけることができました！！

<img width="443" alt="t_comp" src="https://user-images.githubusercontent.com/34936885/64613572-6d03aa00-d411-11e9-8c2a-376656013ad4.png">

#### フラグの設定場所
手順の9.のフラグの追加場所ですがBuild Settingsにはフラグを設定できる場所が下記のようにいくつかあります。

* Apple Clang - Preprocessing → Preprocessor Macros  
→ だめ。Objective-Cの遺産です。Swiftを使うならやめましょう。
* Swift Compiler - Custom Flags → Other Swift Flags  
→ だめ。ちょっと古いやつ。書き方が多少めんどくさいです。
* Swift Compiler - Custom Flags → Active Compilation Conditions  
→ *ココ*。ここに書きましょう。

### 評価
この方法はべつにいいけど...

同一プロジェクトで複数アプリを作成することができましたが...引き継ぐ人たちのことも考えてほしい。

ターゲットが複数あるとあるターゲットにだけファイルを追加し忘れることが稀によくあります。クラスファイルならまだビルド実行時に気づけますが、xibファイルなどの場合はその画面を表示するまで気付くのがなかなか難しいです。

例えばPiyoViewControllerでPiyoView.xibを読み込んでいた場合「本番アプリだけPiyo画面表示したらクラッシュすんねんけど？」のような悲劇が起こります。

<img width="258" alt="t_membership" src="https://user-images.githubusercontent.com/34936885/64613443-1ac28900-d411-11e9-933f-c7cc57d8b511.png">

## おすすめ
3つ目はXcodeのConfigurationsでわける方法です。

### 手順
1. Project→Info→ConfigurationsでDeugを複製する  
<img width="703" alt="c_config" src="https://user-images.githubusercontent.com/34936885/64619332-e1901600-d41c-11e9-80b8-fab43f32e2d7.png">
2. 複製したConfigurationの名称を変更する（Debug copy→Develop）
3. Build Settings→Swift Compiler - Custom Flagsにフラグを追加する（開発ならDEVELOPダミーならDUMMYなど）  
<img width="774" alt="c_flag" src="https://user-images.githubusercontent.com/34936885/64619412-008ea800-d41d-11e9-9921-691cf2c21e1c.png">  
4. Build Settings→Product Bundle IdentifierでBundele idを変更する  
<img width="773" alt="c_id" src="https://user-images.githubusercontent.com/34936885/64619454-143a0e80-d41d-11e9-9404-e33770dafd76.png">
5. Build Settings→Packaging→Product Nameでアプリ名を変更する  
<img width="786" alt="c_product_name" src="https://user-images.githubusercontent.com/34936885/64619722-827ed100-d41d-11e9-80be-ff2e52696b0c.png">
6. Build Settings→Asset Catalog Compiler - Options→Asset Catalog App Icon Set Nameでアプリアイコンを変更する  
<img width="775" alt="c_icon" src="https://user-images.githubusercontent.com/34936885/64619749-90cced00-d41d-11e9-9b77-9a64cf4339b7.png">
7. Manage Schemes...→Duplicateでスキームを複製する  
<img width="771" alt="c_scheme_dup" src="https://user-images.githubusercontent.com/34936885/64619690-72ff8800-d41d-11e9-905a-ca487d884eee.png">
8. スキームの名称を変更する（Copy of PiyoApp→PiyoAppDev）  
<img width="904" alt="c_scheme_name" src="https://user-images.githubusercontent.com/34936885/64619649-63803f00-d41d-11e9-91a5-17afcb4e8c8c.png">
9. スキームのBuild Configrationを変更する（Run以外のTestなども適宜変更する）  
<img width="901" alt="c_scheme_bu" src="https://user-images.githubusercontent.com/34936885/64619605-53685f80-d41d-11e9-8bee-bc1f67642477.png">
<img width="175" alt="c_scheme_build" src="https://user-images.githubusercontent.com/34936885/64619550-40ee2600-d41d-11e9-8f34-8ebff6753ece.png">
10. Dummyも同じように作成する
11. それぞれの環境のサーバの接続先をコードで設定する  

```swift
var serverURL: String {
        #if DEVELOP
        // 開発用URL
        return "https://example.com/piyoDev"
        #elseif DUMMY
        // ダミー用URL(ダミーはローカルのJSONファイル読み込む想定なので空文字でもOK)
        return "https://example.com/piyoDummy"
        #else
        // 本番用URL
        return "https://example.com/piyo"
        #endif
    }
```

これで要件通り3つのアプリにわけることができました！！(なぜか小さいアイコンが全部緑になったけどビルドしたらそれぞれ違うアイコンが表示されます)

<img width="1051" alt="c_comp" src="https://user-images.githubusercontent.com/34936885/64619520-2d42bf80-d41d-11e9-93d9-d29acb3a93b0.png">

### 評価
この方法がおすすめ！！

不必要にブランチを増やしたり、無駄にターゲットを増やす必要もなし！！管理も楽！！これがおすすめ！！

# さいごに
タイトルにベストプラクティスと書きましたが１回使ってみたかっただけです。他にこんな方法があるよとかこの方法のがいいよとかあればぜひ教えてくださいmm