サーバクライアントなアプリを作成してみる

## このページについて

学習目的で、サーバクライアント式のスマートフォンアプリケーションを組んでみました。
本記事は、実装に当たって参考にしたサイトをまとめたリファレンス記事となります。
1画面、1GetAPIですが、やることは沢山あり大変勉強になりました。

***
【全体図】
![ぷれぜんてーしょん１概要図.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/96b2181e-22d6-456f-9e13-d3769ea76c2f.png)

***
## 開発環境を準備する

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/d1f2d41c-ee4c-afb3-be61-a97a7b724e4b.png)　
Server開発環境はいつも使っているEclipse。特にコメントなし。

 * [GitHubとEclipseの連携とかまとめ](https://qiita.com/komikcomik/items/207794a332aa581c22d4)

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/b78e44f2-d577-a68e-b628-0ada044c9013.png)![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/931fb06c-9d01-162d-d82f-ebccd7b72637.png)
デザインツールにはBootstrap Studioを採用。
プロのデザイナー向けでは無い気がしますが、
私の様な非デザイナーがデザインする場合、

 * 種々のデザインテンプレートが用意されている
 * GUIベースで作成したデザインのHTML/CSSを自動出力してくれる

この2点が大変重宝します。

3000円位のシェアウェアですが、永久ライセンスで追加コストが無い点も〇。

 * [最高のモックアップツールかもしれないBootstrap Studio](https://qiita.com/Yuta_Fujiwara/items/10df62b820d056a92e86)

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/e4a7336d-9777-eac6-434a-2fdfe39c33cf.png)![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/98afb0a8-21d7-35cd-463c-9a8d42d3fc49.png)![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/119f3e4c-0970-c425-7d37-9251d0aa7aba.png)
今回、フロントエンド開発はCORDOVAを採用しました。理由は2点。

 * iOS, Androidの両方に対してアプリケーションをリリースしたい
 * 従来のWeb技術をベースに構築出来るため、学習コストの圧縮が期待出来る

Monacaはフロントエンド開発に対する統合開発環境で、実装からビルドまで実行することが出来ます。無料枠あり。神。

 * [monacaでスマホアプリを作ろう #1](https://qiita.com/furu8ma/items/42b8c96ed11c7ed22bfe)

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/b9e569d1-91e6-493d-bee9-9e87f7910d70.png)
circleciは、Jenkins等の様なビルドツールです。無料枠があります。
本当はDocker&Jenkinsの予定でしたが、サーバ費用負担を減らすため没に。
今回はServerのCIツールのみ実施しました。

 * [公式HP](https://circleci.com/ja/product/)　※チュートリアルを試して理解するのが手っ取り早い
 * [いまさらだけどCircleCIに入門したので分かりやすくまとめてみた](https://qiita.com/gold-kou/items/4c7e62434af455e977c2)

***
## SpringBootでRestAPI Serviceを構築する

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/5e344a4f-8041-82ea-1e9e-14914e78ae85.png)![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/233171a4-2099-d4ad-bdb2-89781665ff70.png) ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/bcc9c95b-e8fe-2a2d-5e8b-bdde9f0978fa.png)
SpringBootでHelloWorldを動かす所からはじめて、次にRestAPIへと拡張させました。

 * [SpringBoot入門...いいから動確だ！](https://qiita.com/ketman55/items/16d1e491a5a493f71c92)
 * [Spring BootとJPAでREST APIを実装する(アプリケーション層編)](https://qiita.com/YutaKase6/items/487edfa9f6e39ac2f939)
 * [Rest API(GET)を作ってみる](http://poppingcarp.com/spring-boot_intro_rest_get/)
 * [Spring MVC コントローラの引数](https://qiita.com/MizoguchiKenji/items/2a041f3a3eb13274e55c)

***
一人開発もあり命名規則は適当になってしまったが、先に見て実践すればよかったと思う記事。

 * [Naming -名前付け-](https://qiita.com/Koki_jp/items/f3d3e824f98d182d4100)

***
## カバレッジを見ながらソースとテストコードを詰めていく

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/c33c6456-eee1-30bc-fcda-9aec46cf8221.png)　![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/d95c0727-ad7b-5289-3ccd-e5cf312af388.png)
テストコードはSpock、カバレッジ計測はJacocoを利用しました。
今更ながら初めてテストコード、カバレッジレポートを使いましたが、大変有用ですね。
ソースコードとテストコードが相互に堅確になっていく過程が嬉しい＆楽しかったです。

***
JUnitは可読性に課題があるとのことでSpockを採用しましたが、こちらも非常に扱いやすかった。

 * [JavaのテストGroovyでいいのではないかという話](https://www.slideshare.net/disc99_/javagroovy-65909637)
 * [JavaのユニットテストにSpockを適用する](https://qiita.com/euno7/items/1e834d3d58da3e659f92)
 * [Spockノウハウの簡単なまとめ](https://qiita.com/it__ssei/items/16f7ffd640dac221d9f9)

***
カバレッジは活躍する範囲、補うべきテストケースを考える機会になりました。

 * [Jacoco...Gradle JaCoCoプラグインでカバレッジを取る](https://qiita.com/tq_jappy/items/a312c99d33b27fb5d383)
 * [テストカバレッジ100%を追求しても品質は高くならない理由と推奨されるカバレッジの目標値について](https://qiita.com/bremen/items/d02eb38e790b93f44728)

***
## APIのドキュメントを作成する

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/a3ad336e-00e9-0404-fed8-2be6ac9867e3.png) ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/925eae5f-ba4e-5bee-7562-e046edb38c40.png)
Swaggerに依頼。GradleにSpringFOXを、mainクラスに説明文章などを記載すればOK。

 * [SpringBootを使ってSwaggerに入門してみた](https://qiita.com/shuhey_fujiwara/items/e3bfd8d6deaaa22d618c)

***
## デプロイ環境を構築する

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/b7265a33-d708-cca5-4816-60f3f63aa84c.png)　![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/0a3dcd00-e5e5-126d-fa80-1ef9dc4cc5b5.png)
AWSが理想でしたが、学習コストの都合で扱いなれた月額性のCentOSサーバを借りることにしました。

 * [さくらのVPS 1GB2コア 約990円/月](https://vps.sakura.ad.jp/)

***
##### やること１．Teraterm, WinSPCを使って作業出来るようにする

 * [初心者でもわかる！さくらVPS | Sakura VPS マニュアル](http://www.xn--vps-073b3a72a.com/4.html)
 * [さくらVPSでCentOS7 ７．sftp接続](https://qiita.com/Qsugi/items/a8328a116218b058a8bf)

***
##### やること２．SpringBootが動くようにJDKをインストールする

 * [Java: Linux (CentOS)からJDK (RPM PKG版)をアンインストールする方法](https://yukun.info/linux-uninstall-java-jdk/)
 * [CentOSにJDK、Tomcatをyumでインストールしてしまったものを最新にするとき](https://qiita.com/yoh-nak/items/a93d2564ccf574065970)
 * [CentOS7 + OpenJDK11 + Tomcat9　動作環境構築](https://ufirst.jp/memo/2019/03/18/centos7-openjdk11-tomcat%E3%80%80%E5%8B%95%E4%BD%9C%E7%92%B0%E5%A2%83%E6%A7%8B%E7%AF%89/)

***
##### やること３．SpringBootのJarをデプロイ&稼働確認

SpringBootはTomcatが内包されており、Tomcatサーバを立てずともjar単独で実行できます。

【Step1.とりあえず動かしてみる】
① jarをサーバへ転送(WinSCPで手送り)
② java jar （手送りしたjarのパス） でサービス実行
③ http://(サーバIP):8080/ で稼働確認

【Step2.常駐サービスとして登録する】
実際のサービスインに当たっては以下の作業を行って常駐化させています。

 * [Spring Boot 2 アプリケーションのデーモン化](https://kcf-developers.hatenablog.jp/entry/2018/04/20/182217)

***
## CORSに対応する

***
ここまで進めると、サーバ・クライアントそれぞれで実装が進められる様になります。
一方、実際に結合して通信するには、CORS（Cross-Origin Resource Sharing）に対応する必要があります。

* [「No 'Access-Control-Allow-Origin' header is present on the requested resource. 」というエラーに遭遇しました](https://qiita.com/tchofu/items/c82c1290a8f27df95399)

***
POSTなど送信する場合はpreflight requestを意識した設定にする必要があります。

 * [SpringによるCross Origin Resource Sharing](https://tech-lab.sios.jp/archives/7620)

***
## SSL通信に対応する

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/ba217ac9-6e2e-5bdb-a8d9-92e9b6227159.png)　![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/86be4ac8-6876-ed4a-8a79-68be265d886a.png)
AndroidのChromeではHTTPSでなければAPIとの通信を許可してくれない様です。
仕方がないので、Server側にSSLを設定しHTTPS通信が出来るようにしました。

***
##### やること１．独自ドメインを設定する

 * [独自ドメインの設定](https://www.sakura-vps.net/original-domain-settings-for-sakura-vps/)

***
##### やること２．SSL証明書を取得する
米国の非営利団体が無料で提供しているLet's Encryptを利用しました。
Let's Encryptの証明書は3ヶ月で有効期限が切れるので、cronを仕込むと良いと思います。
※今回はApacheではなくnginxに管理を頼むので、下記記事内のApache導入箇所は無視して下さい。

 * [無料SSL証明書のLet’s Encryptとは？](https://ssl.sakura.ad.jp/column/letsencrypt/)
 * [ネコでもわかる！さくらのVPS講座 ～第六回「無料SSL証明書 Let’s Encryptを導入しよう」](https://knowledge.sakura.ad.jp/10534/?_ga=2.41140257.2005541064.1572146942-1144306986.1562941947)
 * [CentOSにLet's EncryptのSSL証明書を導入する](https://kohkimakimoto.hatenablog.com/entry/2016/09/15/180119)

***
##### やること３．nginxをインストールしてSSL証明書と紐付ける
nginxを導入した理由はSpringBootに直接SSLを組み込む方法が理解出来なかったためです。。

 * [CentOS 7.0 - Web サーバ Nginx で SSL 接続！](https://www.mk-mode.com/blog/2014/09/13/centos-7-0-setting-of-nginx-ssl-connection/#)

***
## AppStoreに提出する

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/1e9bfbed-e6a8-180a-94e1-e0ea1e0a485b.png)
AppStoreに提出したい場合、リリース版のビルドには原則Mac(Xcode)が必要です。
私はWindowsユーザのため、Monacaのビルドサービスを利用しました。
1アプリケーションに対して3300円でリリース版のビルドを実行してくれます。

***
また、ビルド情報としてデバイスの登録も求められます。
実機デバッグも兼ねて、中古のiPhone6(Bランク)を買いました。約9000円。
コミュ力のあるみんなは、Appleユーザの友達からお古を貰いましょう。

***
iOSアプリを公開するには、審査をPassする必要があります。
NGでもチャットで丁寧にコメントをくれますので、指示に従って修正&再提出しましょう。

 * [[2018年版] よく分かる！iOSアプリのリリース手順のまとめ](https://dev.classmethod.jp/smartphone/iphone/ios-app-how-to-release-2018/)
 * [個人開発者がAppStore用にプライバシーポリシーを書く](https://qiita.com/Hiroki_Kawakami/items/94f012d20afdb692df20)

***
## GooglePlayに提出する

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/372dee1c-0dcf-f5c0-4e8c-d287f95e2bd3.png)
GooglePlayではアプリの審査は無く、必要な情報を追加して提出すればよいです。

 * [AndroidアプリをGooglePlayでリリースする方法【今さら聞けない！】](https://techacademy.jp/magazine/2255)

***
## 出来上がったもの

***
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385780/e283e947-31cd-5210-13f1-9773cf484c3d.png)
古典文章を入力すると、Mecabの形態素結果と一部単語は意味付きで返してくれるアプリ。
妻とテレビを見ていた時に何となく出たアイディアを真に受けたもの。

 * [Kotetsu 古典文章の読解支援アプリ(AppStore)](https://apps.apple.com/us/app/kotetsu-%E5%8F%A4%E5%85%B8%E6%96%87%E7%AB%A0%E3%81%AE%E8%AA%AD%E8%A7%A3%E6%94%AF%E6%8F%B4%E3%82%A2%E3%83%97%E3%83%AA/id1481741983?l=ja&ls=1)
 * [Kotetsu 古典文章の読解支援アプリ(GooglePlay)](https://play.google.com/store/apps/details?id=com.pj.app.ketman)

***
## 最後に（かかった時間とお金）

***
|要素|コスト|
|:--|:--|
|工期|2019年5月～10月(6か月間)|
|工数|180時間くらい(1日1時間を目安に実施)|
|サーバ代|6930円(990円×7か月)|
|AppStore登録料|10000円くらい|
|GoogleDev登録料|3000円くらい|
|Monaca有料プラン|2000円くらい|
|Monacaビルドサービス|3300円|
|中古のiPhone6|9000円くらい|
|BootStrapStudio|3000円くらい|
|合計|37230円くらい|

※Monacaは、ビルドを多用する月のみプランをひとつ上げて使っていました。

***
記事にすると1枚ペラですが、どれも初物で躓きながらの作業となり、時間がかかりました。
お金もそれなりに発生しましたが、(効率を鑑みて)ノーコストに拘るのは辞めて、出す所は出す様に心掛けました。

***
紹介は以上です。
折角こなれたので、エンハンスとか、新しいアプリとかまた作りたいですね。