cordova を使って本気で商用ハイブリッドアプリ開発をやってみた
TRANSCRIPT
Cordova を使って本気で商用ハイブリッドアプリ開発をやってみた第 10 回 Apache Cordova 勉強会
ソニーネットワークコミュニケーションズ ( 株 ) 緒方 信
ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
Agenda 自己紹介 プロジェクト概要 教科書では教えてくれないハイブリッドアプリ開発 現場で役立つ小技集 通信簿 まとめ
2 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
自己紹介 緒方 信
◦ ソフトウェアアーキテクト◦ プログラマ◦ 元 PC アプリ屋さん
◦ C/C++ が好き◦ 人類はデストラクタという発明をもっと大切にすべきだと考えている
3 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
プロジェクト概要
4 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
クライアントアプリ概要 – 主な機能 ほかのアプリとの差別化をはかるメイン UI
◦ 楽しい高速スクロール デジタルコンテンツの作成
◦ スマートフォン内の写真を使って簡単操作 デジタルコンテンツを機器へ転送
◦ 専用フォーマットに変換◦ Bluetooth Low Energy (BLE) で転送
ほかにもたくさん
5 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
開発環境・仕向け Cordova 6.1.1
◦ Cordova android 5.1.1◦ Cordova ios 4.1.1
Node.js 4.5.0◦ Npm 2.14.7
TypeScript 1.8.10
SASS (SCSS)◦ Compass 1.0.3
6 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
Android 5+, iOS 9+◦ 比較的新しいデバイスのみサポート◦ タブレット用に最適化はしない
対応言語◦ 日 , 米 , 中 ( 簡体字 )
教科書では教えてくれないハイブリッドアプリ開発 元 PC アプリ屋が考えたアプリ開発の大方針
7 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
ハイブリッドアプリとは ?
Java/Objective-C/C++
Hybrid フレームワーク
JavaScript
・ Native 通信用 API を通じてデータをやり取り・プラグイン機構を用いて機能拡張
アプリ
ブラウザコンポーネント
• 普通のアプリとして動作• ブラウザコンポーネント上で Web 技術を活用
8 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
ウェブアプリとネイティブアプリのいいとこどり ?ウェブアプリ ネイティブアプリ
Pros ・複数 OS 対応コストが低いブラウザで動けばよい
・リアルタイムに更新できるサーバー上にデプロイすることで、すべてのユーザーが更新されたものにアクセス可能
・技術者の数が多いWeb アプリのフロントエンド開発者 >特定プラットフォームの Native アプリ開発者
・高いパフォーマンスプラットフォームに最適化
・ユーザへのタッチポイントが多いストアから配信Home 画面やランチャーに登録される
・ H/W リソースへのアクセスが容易OS が API を公開
Cons ・操作性やレスポンスが悪いネットワーク状態に依存するNative アプリほど最適化されていない
・ユーザーへのタッチポイントが少ないストアに置けないブックマーク登録が基本
・ H/W リソースへのアクセスが限定的HTML5 で策定される API のみ使用可
・複数 OS 対応コストが高いプラットフォームごとにコードベースが必要になる
・リアルタイムに更新できないストアによってはアップデートごとに申請が必要ユーザーは必ずしも最新版を使用するとは限らない
・サービスに誘導しにくいSNS で拡散されても、アプリをダウンロードしてもらわないと使ってもらえない
ハイブリッドアプリPros ・複数 OS 対応コストが低い
ブラウザで動けばよい ※ プラットフォーム依存を最小化・リアルタイムに更新できる
サーバー上にデプロイすることで、すべてのユーザーが更新されたものにアクセス可能 ※ リソースをサーバーに置くことも可能
・技術者の数が多いWeb アプリのフロントエンド開発者 >特定プラットフォームの Native アプリ開発者
・高いパフォーマンスプラットフォームに最適化 ※ コストのかかる処理は Native で
・ユーザへのタッチポイントが多いストアから配信Home 画面やランチャーに登録される
・ H/W リソースへのアクセスが容易OS が API を公開 ※ 必要に応じてプラグインを実装
Cons ・操作性やレスポンスが悪いネットワーク状態に依存するNative アプリほど最適化されていない
・ユーザーへのタッチポイントが少ないストアに置けないブックマーク登録が基本
・ H/W リソースへのアクセスが限定的HTML5 で策定される API のみ使用可
・複数 OS 対応コストが高いプラットフォームごとにコードベースが必要になる
・リアルタイムに更新できないストアによってはアップデートごとに申請が必要ユーザーは必ずしも最新版を使用するとは限らない
・サービスに誘導しにくいSNS で拡散されても、アプリをダウンロードしてもらわないと使ってもらえない
建前です
9 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
商用ハイブリッドアプリとしての宿命 初見でブラウザだなと思われたら…
ユーザーの期待値は常にネイティブアプリ◦ 「ハイブリッドアプリだからしょうがないねー」とはならず、容赦なく低評価が付くことになる
負けです
商用アプリとして成立させるにはなにをすべきか ?そのための方針を最初に立てておく必要がある10 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
商用ハイブリッドアプリ開発って ?ネイティブアプリ開発では”あたりまえ”とのギャップをなくす
◦ ハイブリッドアプリ開発のほうがコストがかかっては本末転倒◦ ウェブアプリではなくネイティブアプリの挙動
「作っておしまい」ではなく妥協なき商品力を追及する◦ プロが定義するユーザーインターフェイスの実現◦ なんでもありとせず、保守まで見据えた秩序の確立
11 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
” あたりまえ”とのギャップをなくす開発言語とフレームワーク選定
◦選定理由自然な画面遷移とは
◦画面遷移のメカニズムと工夫ローカライズに関して
◦リソース管理と運用12 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
” あたりまえ”とのギャップをなくす開発言語とフレームワーク選定
◦選定理由自然な画面遷移とは
◦画面遷移のメカニズムと工夫ローカライズに関して
◦リソース管理と運用13 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
開発言語TypeScript
◦ C/C++, Java 経験エンジニアにはとっつきやすい◦ クラスサポートによりオブジェクト指向設計のノウハウをコードに反映しやすい◦ もともと ES2015 の仕様の先取りという感覚だったので、廃れる不安はなし
何よりも強力な型付けで安心我々はコンパイルに対して何のためらいもない
14 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
フレームワークはなぜ必要なのか ?
https://www.slideshare.net/AsialCorp/angularonsen-uihtml5
アプリFoundation/UIKit
Objective-C/Swift
iOS
アプリAndroid SDK
Java
Android
アプリ!
ブラウザ /Cordova
iOS/Android
Android SDK Foundation/UIKit
15 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
半年ごとに誕生する HOT なフレームワーク
http://paiza.hatenablog.com/entry/2015/03/11/Backbone_JS%E3%81%8B%E3%82%89Angular2%E3%81%BE%E3%81%A7%E3%80%81%E5%85%A89%E5%A4%A7JavaScript%E3%83%95%E3%83%AC%E3%83%BC%E3%83%A0%E3%83%AF%E3%83%BC%E3%82%AF%E3%82%92%E6%9B%B8%E3%81%8D%E6%AF%94%E3%81%B9
2009 2013 2015
16 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
さて今回のミッションは… 最新の JavaScript の動向を追い、次期トレンドに乗り遅れるな !
常に研究し自分を高め、エバンジェリストであり続けろ ! 地雷はすべて踏め !
限られた時間とリソースで、個性的な楽しい商品を供給しろ !
最新の JavaScript の動向を追い、次期トレンドに乗り遅れるな !
常に研究し自分を高め、エバンジェリストであり続けろ ! 地雷はすべて踏め !
限られた時間とリソースで、個性的な楽しい商品を供給しろ !
17 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
jQuery Mobile + Backbone.js + i18next
◦オリジナル UI の実装のしやすさ◦ ほかの OSS と組み合わせやすさ◦ 開発チームの専門性
今回は”おとなしめ”なもの 商品開発では枯れたものを採用したい
※2016年初期のお話
フレームワークの足りない機能は拡張する
18 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
シンプルに倒す
” あたりまえ”とのギャップをなくす開発言語とフレームワーク選定
◦選定理由自然な画面遷移とは
◦画面遷移のメカニズムと工夫ローカライズに関して
◦リソース管理と運用19 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
画面遷移とページスタックのメカニズムブラウザの履歴とページスタックを連動
◦ Backbone.Router オブジェクトと jQuery Mobile の changePage() を連携◦ 実際には $.mobile.navigate.history.stack と hash を連動
◦ Android の H/W Back Key のイベントでもブラウザの履歴を戻れば画面遷移可能◦ イベントは Cordova がサポート
A B
"file:///android_asset/www/index.html#A"
"file:///android_asset/www/index.html#B"c
"file:///android_asset/www/index.html#C"
URL history
20 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
画面遷移あるある物語対策ページスタック◦[A]→[B]→[a]→[b]→[c]→[B]
◦×[A]→[B]→[a]→[b]→[c]←[B]◦◎[A]←[B]
◦[A]→[B]→[a]→[b]→[c]→[B]◦[A]→[B]→[a]→[b]→[c]→[B]
A B
a b c
Sub Flow
“Sub Flow” という特別な区間を定義し、終了するときにその区間の履歴を破棄21 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
” あたりまえ”とのギャップをなくす開発言語とフレームワーク選定
◦選定理由自然な画面遷移とは
◦画面遷移のメカニズムと工夫ローカライズに関して
◦リソース管理と運用22 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
ローカライズリソース管理と運用 マスターデータは Excel で管理
◦外部ベンダーとのやり取りに実績があるフォーマット◦ Excel → i18next 用 json を生成するスクリプトを用意
"pattern": {"save": { "title": "SAVE", “description”: “名前をつけて保存 ", "unavailable": "{{param}} は使用できません。 ", "unavailableCharacter": " 使用できない文字が含まれています。", "limitString": "{{numOfString}}文字以内で入力してください。 " },},
ローカライズは運用まで含めて最初に決めておくことが大事23 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
妥協なき商品力の追及ユーザーインターフェイス実現のために◦基本の UI コンポーネント
非同期処理との向き合い方◦保守まで見据えた実装方針
24 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
妥協なき商品力の追及ユーザーインターフェイス実現のために◦基本の UI コンポーネント
非同期処理との向き合い方◦保守まで見据えた実装方針
25 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
商用アプリのユーザーインターフェイス アプリの差別化が図れるメイン画面
26 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
商用アプリのユーザーインターフェイス プラットフォームガイドラインに準拠した画面
27 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
プラットフォームテイスト対応jQuery Mobile の UI の骨組みを作る CSS に加えAndroid Material Design, iOS System Design に対応した CSS を適用
本当に力を入れたい差別化 UI に集中できる28 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
CSS には無茶が効く ? Modernizr のようなアプローチで実現 https://modernizr.com/
<!DOCTYPE html><html class=“platform-android”>:</html>
.platform-android .ui-radio .ui-btn:after { border-color: green;}
<!DOCTYPE html><html class=“platform-ios”>:</html>
.platform-ios .ui-radio .ui-btn:after { border-color: white;}
起動に時間がかかる Android の場合でも処理のうちの 2% ほど29 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
妥協なき商品力の追及ユーザーインターフェイス実現のために◦基本の UI コンポーネント
非同期処理との向き合い方◦保守まで見据えた実装方針
30 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
はじめてハイブリッドアプリを書いた時の思い出 JavaScript では 1度非同期処理をはさむと
同期処理には戻れない ! sleep()
WaitForSingleObject()
ところが非同期処理を使う機会は意外に多い◦ Network 処理 (XmlHttpRequest)◦ Cordova の Native JavaScript の bridge 界面
キミ達も for 文の中に非同期処理が入り込んでしまい、慌てたことがあることを私は知っている。31 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
Promise オブジェクト 非同期処理はコールバック地獄を避けるため Promise オブジェクトなどを導入するのが一般的
◦ ES6 Promise, Q.js, jQueryPromise, e.t.c function procPipeline(): JQueryPromise<SomeData> { let df = $.Deferred();
async1() .then(() => { return async2(); }) .done(() => { df.resolve({ somedata: "hoge" }); }) .fail((error) => { df.reject(error); });
return df.promise();}
32 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
View A
約束を破りたいときもある
現実問題として非同期処理はクライアントの都合でキャンセルできる必要がある
View BView A ■ごとにリクエストを発行するようなシチュエーション画面が切り替わるため、リクエストをキャンセルしたいしかし DOM を削除したとしても…リクエストはキャンセルされず、実行され続ける
33 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
ためしに約束を破れるようにしてみたら処理が統一できてワロタ abort() を追加するファクトリメソッド
◦ jQueryXHR 互換 任意のタイミングで abort() 可
◦ reject() が発火 さらに管理オブジェクトを導入
◦同時に複数の非同期処理を行う場合 画面遷移時に非同期処理を中止可能に
◦管理オブジェクトの cancel() を呼ぶと配下の abort() 呼び出す。
function async(): IPromise<SomeData> { let df = $.Deferred(); let promise = makePromise(df); : return promise;}
let promise = async();setTimeout(() => { promise.abort(); });
let manager = new PromiseManager();manager.add(async1());manager.add(async2());
manager.cancel();
実際にはパイプライン処理内で複数の Promise を連鎖でき、もう少しだけ高機能34 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
元 PC アプリ屋が考えたアプリ開発の大方針独特な案件に対応しやすいフレームワーク画面遷移対応ローカライズ運用基本 UI コンポーネント対応統一された非同期処理
35 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
現場で役立つ小技集 引き出しの数が多ければ、百戦危うからず
36 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
本日のレシピネイティブ連携どうしてる ?
スタブは開発を救う
37 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
ネイティブ連携に Cordova Plugin 化は必須なの ? 通常 Cordova では JavaScript Native 連携に プラグイン化が必要
Plugin.xml JS impl Native
impl
Cordova Plugin
$ cordova plugin add <cordova-plugin-id>+
コレってコストが高く感じられること、ありませんか ?
ネイティブの SDK を一発叩きたいだけなのに ..
この機能、このアプリでしか使わないよ…名前つけんの超メンドクセーアレっ ?そもそも Plugin.xml ってどう書くんだっけ ?
38 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
そんなあなたに cordova-plugin-cdp-nativebridge
https://github.com/sony/cordova-plugin-cdp-nativebridge
この汎用の Native Bridge Plugin を導入すれば、クラス定義を JavaScript レイヤと Native レイヤで行うだけで、対応するメソッドが反応するようになるゾ !!
NativeBridge.Gate
SomeFeature+ coolMethod
.ts(.js)
NativeBridge.Gate
SomeFeature+ coolMethod
.javaNativeBridge.Gate
SomeFeature+ coolMethod
.m
// インスタンスを作成var native = new SomeFeature();
// メソッド呼び出しnative.coolMethod(1, false, "test", { ok: true }) .done((result: CDP.NativeBridge.IResult) => { // 成功}) .fail((error: CDP.NativeBridge.IResult) => { // 失敗});
39 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
スマートフォン内の画像一覧の作成こんなところに使いました
DateTime Picker のフォーカス解除イベント取得
ステータスバーテキストカラーの変更
いつでもネイティブを呼び出せるという安心感が違います40 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
開発者の本音 実機デバッグは大切だ ! なぜなら真実はいつもそこにあるから
UI がうまく動いているか確認するために、JavaScript 側のビジネスロジック通したいだけなんだよね。ネイティブ機能をチェックしたいわけじゃないし。… っていうかハードウェアまだ手元に無いし。そもそもオレ、 Mac のキーボードまだあんまし慣れてないし…
建前です
実機デバッグは大切だ ! なぜなら真実はいつもそこにあるから
41 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
できるだけ PC 開発で引っ張れるようにする スタブ実装と切り替え UI という裏口を準備しよう
◦外部システムとの界面◦ プラットフォームの差異界面
※ ほとんどの cordova plugin は browser プラットフォーム非対応
JavaScript の柔軟性を活用しよう◦ prototype を上書きしちゃえばいいじゃない◦ TypeScript でも any キャストで private メソッドを呼び出せる
ユースケースであればブラウザで確認可能にただし、商品コードには影響がでないように注意しよう42 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
通信簿 簡単なメトリクスの紹介
43 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
コードメトリクス LOC◦TypeScript: 23,160◦SASS(SCSS): 6,027◦HTML (template): 1,072※OSS およびスタブコードを除く
GitHub トレンド※ リポジトリには OSS を含んでいる44
今回利用した OSS
34 種類 ・ Cordova Plugin: 16・ JavaScript Library: 18
ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
Halstead complexity measureshttps://en.wikipedia.org/wiki/Halstead_complexity_measures
plato https://github.com/es-analysis/platoを用いて数値化 LOC (SLOC, LLOC) プログラムの規模 functions ファイルあたりの関数の数 maintainability 保守容易性指数 0 ~ 100 であらわされ、高いほどよい deliveredBugs ファイル単位あたりのバグ発生量の見積もり . 低いほどよい difficulty 理解性 , プログラムの書きやすさの指数 . 低いほどよい
45 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
機能別 LLOC
機能別の規模がわかる46 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1
部
機能モジュールごとの OSS との比較
47 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
まとめ まとめと所感
48 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部
商用ハイブリッドアプリ開発は キチンと準備して臨めば結果はついてくる
◦ ネイティブアプリ開発とのギャップの解消◦ 商品力向上のためにどのような対策が必要か
一昔前とは状況が異なり、技術面で詰まったことはほとんどなかった◦ マルチプラットフォーム対応するなら十分に選択肢のひとつになる
コンシューマー向けアプリ開発はソフトウェアエンジニアにとって花形だと思っています。 もし皆さんにも機会があるとき、ここで紹介させていただいた情報が少しでもお役に立てば幸いです。
49 ソニーネットワークコミュニケーションズ (株 ) クラウド&サービスアプリ開発運用部門 1部