iOS/AndroidでiBeaconを扱うTitaniumモジュールについて調べてみた
Titaniumで、iOSとAndroid両方でiBeaconを扱うアプリを作ってみようかと思い、それらしいモジュールを探してみました。
さらに、どうせTitaniumでやるのであれば、なるべく処理を共通化できると良いなということで、まずはそれぞれで提供されているAPIを比較してみることに。
対象モジュール
今回使おうとしているのは以下のモジュールです。
プラットフォーム | モジュール | バージョン | オリジナル |
---|---|---|---|
iOS | Sensimity/TiBeacons | 0.11.1 | jbeuckm/TiBeacons |
Android | Sensimity/android-altbeacon-module | 1.4.0 | dwk5123/android-altbeacon-module |
探していたところ、どちらも Sensimity というBeacon Management Systemのサービスを提供している会社の GitHub で公開されているものに行き着きました。
どちらのモジュールもオリジナルは別の人が開発したものなのですが、それらをフォークして改善が加わっているバージョンが公開されていて、さらにBeacon Managementしている会社のものであれば信頼性も高いのではということで、これを使ってみることにしました。
APIを比較
それぞれのモジュールに用意されているAPIを比較。
主要なAPIは同じ構成になっているので、挙動の差異が少なければ、共通化できそう。
それ以外は、直接iBeaconを扱えないAndroid用モジュールに、そのあたりをカバーするためのAPIが用意されている感じ。
API | TiBeacons | android-altbeacon-module | 関連イベント |
---|---|---|---|
アドバタイズ開始 | TiBeacons.startAdvertisingBeacon() | Altbeacon.startBeaconAdvertisement() ※1 | advertisingStatus |
アドバタイズ停止 | TiBeacons.stopAdvertisingBeacon() | Altbeacon.stopBeaconAdvertisement() ※1 | - |
モニタリング開始 | TiBeacons.startMonitoringForRegion() | Altbeacon.startMonitoringForRegion() | enteredRegion, exitedRegion, determinedRegionState |
全てのモニタリング停止 | TiBeacons.stopMonitoringAllRegions() | Altbeacon.stopMonitoringAllRegions() | - |
ビーコンとの距離測定 | TiBeacons.startRangingForBeacons() | Altbeacon.startRangingForBeacons() (Altbeacon.startRangingForRegion()) |
beaconRanges, beaconProximity |
全ての距離測定を停止 | TiBeacons.stopRangingForAllBeacons() | Altbeacon.stopRangingForAllBeacons() | - |
BLEサポート有無 | TiBeacons.isBLESupported() | Altbeacon.isBLESupported() | - |
BLE有効無効 | - | Altbeacon.checkAvailability() | - |
Bluetoothの状態確認 | TiBeacons.requestBluetoothStatus() | - | bluetoothStatus |
Beaconサービスへ接続 | - | Altbeacon.bindBeaconService() | - |
Beaconサービスへの接続を解除 | - | Altbeacon.unbindBeaconService() | - |
Beaconサービスとの接続状態確認 | - | Altbeacon.beaconServiceIsBound() | - |
バックグラウンド動作設定 | - | Altbeacon.setBackgroundMode() | - |
ビーコンレイアウト追加 | - | Altbeacon.addBeaconLayout() | - |
ビーコンレイアウト削除 | - | Altbeacon.removeBeaconLayout() | - |
距離測定間隔設定 | - | Altbeacon.setProximityBounds() | - |
自動測定を有効化 | ※2 | Altbeacon.enableAutoRanging() | - |
自動測定を無効化 | ※2 | Altbeacon.disableAutoRanging() | - |
自動測定の有効無効 | - | Altbeacon.setAutoRange(boolean autoRange) | - |
サービス内動作設定 | - | Altbeacon.setRunInService(boolean runInService) | - |
サービス内動作確認 | - | Altbeacon.isRunInService() | - |
測定間隔の設定 | - | Altbeacon.setScanPeriods(scanPeriods) | - |
補足
- ※1 Altbeacon.start(stop)BeaconAdvertisement() は完全にテストされていないもよう
- ※2 TiBeacons.enable(disable)AutoRanging() はあったが0.8で廃止されたもよう(APIだけ残っている)
イベント
iBeaconを扱う際に発生するイベントは以下のとおり。
イベント名は双方同じものを使っているようなので、この点も挙動の差異次第で共通化できそう。
イベント | 内容 |
---|---|
advertisingStatus | アドバタイズ状態 |
bluetoothStatus | iOSのみ。Bluetooth状態 |
enteredRegion | 領域侵入 |
exitedRegion | 領域退出 |
determinedRegionState | 領域状態を測定 |
beaconRanges | 領域検出 |
beaconProximity | ビーコンとの距離測定結果 |
changeAuthorizationStatus | iOSのみ。パーミッション状態の変化 |
まとめ
当然細かい挙動は違ってくるのだと思いますが、API構成などはほぼ同じようなので、基本的な流れは共通化できそうな印象。
次は実際に組み込んでみて検証してみる予定。
- 作者: 上原昭宏
- 発売日: 2014/03/25
- メディア: Kindle版
- この商品を含むブログを見る
BacklogのSubversionリポジトリをバックアップ
お仕事ではプロジェクト管理ツールとして Backlog を使っています。
年度末ということもあってプロジェクトの整理をしていたところ、過去に使っていたSubversionリポジトリをバックアップする必要がでてきたので、やり方を調べてみました。
リポジトリをエクスポート
いくつかやり方はあるなかで、もっとも一般的と思われる svnadmin dump
をしてみようと思ったのですが。
$ svnadmin dump <REPO_PATH> > <DUMP_FILE>
ひとつ問題があり、それは svnadmin dump
時に指定するエクスポート元のリポジトリは、ローカルのパスでないとダメだということ。
数が多くなければそれでも良いのですが、やはり複数のリポジトリをチェックアウトしてダンプして…というのを繰り返すのは面倒なので、できればBacklog上のリポジトリURL( https://<SPACE_KEY>.backlog.jp/subversion/<PROJECT_KEY>
)からエクスポートしたいところです。
そこで、Backlogでエクスポートする機能などないのかな、と思って調べてみたところ、それ自体はないものの、FAQでバックアップ方法について紹介されているのを発見しました。
Subversionのリポジトリのエクスポートサービスはありますか? | FAQ | Backlog [バックログ]
紹介されているスクリプトを使うと、内部的に svnsync
というミラーリングツールを使って、リポジトリの複製を作ってくれます。
作られた複製はリポジトリのフォルダ構造が再現されている状態なので、そのフォルダをリポジトリパスとして指定することで、 svnadmin dump
にてダンプファイルにまとめることもできました。
リポジトリのインポート
念のため、ダンプファイルからの復元手順も確認。
svnadmin create
で新しいリポジトリを用意し、 svnadmin load
でダンプファイルからインポートすることで、ローカルにリポジトリを復元することができました。
$ svnadmin create <NEW_REPO> # リポジトリを作成 $ svnadmin load <NEW_REPO> < <DUMP_FILE> # ダンプファイルからインポート
ただし、この方法は通常Subversionサーバー上で実施するらしく、少し調べてみましたが、例えばBacklogのような公開されているSubversionリポジトリへ直接インポートする方法は見つけられませんでした。
Backlogでは有料(税抜き30,000円)にてSubversionリポジトリをインポートするオプションを提供しているので、やはりそういった手段はなさそうな印象。
まあ今後はGitを主流に使うでしょうし、バックアップしたSubversionリポジトリは何か合ったときに参照に使う程度なので、今のところ、自分的には問題はなさそうです。
スクリプトをちょっと改良
というわけで、紹介されていたスクリプトをベースに、取り回ししやすいようにダンプファイルを出力して、念のためダンプファイルが読み込めるかを確認するために新しいローカルリポジトリを作成するという処理を追加してみました。
BacklogのSubversionリポジトリをバックアップする
引数にスペースIDとプロジェクトキーを指定して実行すると、ローカルに以下の3つを生成します。
<PROJECT_KEY>
フォルダ ...svnsync
でミラーリングしたSubversionリポジトリの複製<PROJECT_KEY>.dump
ファイル ... 上記をもとに出力したダンプファイル<PROJECT_KEY>_CHECK
フォルダ ... 上記ダンプファイルをインポートした新しいリポジトリ
<PROJECT_KEY>_CHECK
フォルダをsvnXなどで開いてみると、履歴を読み込むことができたので、問題なさそう。
という感じで一通り必要なリポジトリはバックアップできました。
参考
- Subversionのリポジトリのエクスポートサービスはありますか? | FAQ | Backlog [バックログ]
- BacklogのSVNレポジトリを無料でバックアップ | Tokyoish Note
- Backlogのリポジトリを別サーバへ移行したメモ。 - 磁力式駆動
チーム開発実践入門 ~共同作業を円滑に行うツール・メソッド (WEB+DB PRESS plus)
- 作者: 池田尚史,藤倉和明,井上史彰
- 出版社/メーカー: 技術評論社
- 発売日: 2014/04/16
- メディア: 単行本(ソフトカバー)
- この商品を含むブログ (11件) を見る
R-BROS. FEST 2016でGRIM SPANKYとLIFE IS GROOVEを観てきました
3/18(木)、ニコ生で放送している「ロック兄弟」という番組のイベント「R-BROS. FEST 2016」に行ってきました。
一昨年くらいに車のCMで流れていたジャニス・ジョプリンの「MOVE OVER」、てっきり外人さんのカバーなのかなーと思っていたんですけど、歌っているのはGRIM SPANKYという日本人のバンドということを知りまして。
それで聴いてみた彼らのファースト・アルバム「SUNRISE JOURNEY」がカッコよく、さらに先日出たミニアルバム「ワイルド・サイドを行け」が5曲ながら名曲ばかりな感じで、最近のお気に入りアーティストのひとつでした。
これはライブで観てみたいな―とウォッチしていたところ、今回のイベントが行けそうだったので、チケットを申し込むことに。
で、そのイベントは対バン形式で、もう一組アーティストが出演するというので名前を見てみたら、なんとLIFE IS GROOVEではないですか!
実はこちらも以前から気になっていて、かつてTBSで放送されていた「さんまのスーパーからくりテレビ」で天才少年ギタリストとして紹介されていた山岸竜之介君が参加しているバンド。しかもメンバーがRISEのベーシストKenKenに、レジェンド・ムッシュかまやつ氏!年齢差60歳、どんな音を出すのか、非常に気になる!
当日は本編開演時間ギリギリに到着したら、オープニングアクトを務めていたarko lemmingというバンドが終わる頃でした。残念。
ステージ準備中は、OKAMOTO'Sのドラマー・オカモトレイジがDJとして会場を盛り上げていました。
「ロック兄弟」の番組MCの方々の諸々が終わって、いよいよGRIM SPANKY登場!
GRIM SPANKYの魅力のひとつは、やっぱりヴォーカル・松尾レミの声だと思いますが、ライブでのシャウトもかっこ良い。あの声にあの音、ドンピシャです。
疾走感のある「ワイルド・サイドを行け」から始まって、コール&レスポンスが盛り上がる「NEXT ONE」、バラード「大人になったら」などなど、少ない曲数でしたが、堪能しました。
それにしても、ほとんど直立で無表情な感じなのに、指がめっちゃ動いてブイブイやっていたベースの人はどなたなんだろう。
でもって、後半はLIFE IS GROOVE!
ドラム、キーボードに2名のホーン・セクションにお三方という編成。
のっけからKenKenのベースがブリブリ鳴って超ファンキー!ボリュームメーターが2、3個あがったような音圧。
山岸竜之介君は、まだ16歳ですかー。なんだかさわやか好青年になっていてビックリ。
そして、そんな2人を見守るというより見守られながら、飄々とマイペースにステージを彷徨うお茶目なムッシュ。
体を動かさずにはいられなくなる感じのバンドサウンドと、ゆる〜い感じのKenKenのMCとの落差もまた面白かった。
さらにアンコール。
GRIM SPANKYとLIFE IS GROOVEがステージにあがると、KenKenが「GRIM SPANKYとぜひこの曲をやってみたかった」といって始まったのは、あのドラム!そう、MOVE OVER!イベントだし、対バン形式で曲数少ないし、まさか演奏するとは思っていなかった!
あの声でMOVE OVER、やっぱりカッコよい。
しかも何がスゴいって、下北沢のジャニスの息子と同じステージにいるんですよね。
その後もスパイダースの「バン・バン・バン」を全員で演奏!そのどさくさに紛れてムッシュにサインをもらうオカモトズ・レイジ(笑)
いやー、とっても濃厚なイベントでした。
GRIM SPANKYは4月に「“ワイルド・サイドを行け”ツアー」をはじめ、イベントにも多数出演予定のようなので、詳しくは 公式サイト をどうぞ。
LIFE IS GROOVEは4/27にシングルが出るそうで、発売記念的なイベントもあるようなので、こっちも LIFE IS GROOVE OFFICIAL SITE をチェック。
どちらも改めて単独公演で観てみたいなー。
ロック兄弟、番組自体は観たことがないけど、最高なイベントをありがとうございました。
- アーティスト: GLIM SPANKY,松尾レミ,いしわたり淳治,亀本寛貴,亀田誠治
- 出版社/メーカー: ユニバーサル ミュージック
- 発売日: 2016/01/27
- メディア: CD
- この商品を含むブログを見る
- アーティスト: LIFE IS GROOVE
- 出版社/メーカー: TENSAIBAKA RECORDS
- 発売日: 2015/11/11
- メディア: CD
- この商品を含むブログを見る
Titaniumもくもく会に参加しました
先週のことですが、久々にTitanium仲間のゆる〜い集まりがありました。
ひさびさ〜と思ったら、去年の Twilio & Titaniumミートアップに行ってきました - Umi Uyuraのブログ 以来ぶりだったんですね。
1月には新年会があったようですが、私は都合があわず参加できなかったので、半年以上ぶりの集まりでした。
Titaniumもくもく会 - Titanium | Doorkeeper
以下、発表された方のメモです。
Titanium周りの最新動向 - @kaz_konnoさん
まずは @kaz_konnoさん からTitaniumの最新動向について・・・ということだったのですが、特にないとのこと(笑)
とは言え、やはり年初に飛び込んできたAxway社によるAppceleratorの買収のニュースは驚きでした。
Axway Acquires Appcelerator—And Why This is Great News for All
Axwayという会社についてはよく知らないのですが、エンタープライズ向けの製品をいろいろと持っているところのようです。
まさかTitanium終了か!?という懸念もありましたが、今のところ製品・サービスラインナップはこれまでと変わりなく提供されるようなので、一安心。
Co-FounderのJeffもそういった相手を選んでの決断だったのではないか、ということでした。
Indie foreverプランについて
昨年、Appcelerator Platformという基本有料のサービス体系に変わってから、それ以前にTitaniumアカウントを持っていれば、Indieを永久無料で使えるというプランが期間限定で提供されていました。
このプランへの切り替えは、本来は昨年の6/30までに以降手続きが必要で、もう終了しています。
ただ、この切替方法が少々わかりにくく、実は新しいアカウントに切り替わった時点では Developer プランという状態で、アカウントの設定から Indie に手動でプランを変更しないといけないのです。
これに気づかずに Indie へ切り替えそこねてしまった人も多いようで、期限を過ぎてしばらくは直接サポートに連絡するなどしてIndieに切り替えてもらったようなケースもあるようですが、その救済措置も終了ということのようです。
Developer Portal
Developer向けのポータルページが新しくなりました。
最新情報は Appcelerator Developer Updates というページに集約されているようなので、Titanium/Appcelerator Platformに関して情報が欲しい人は、定期的にこちらをチェックすると良いでしょうとのこと。
公式のDeveloper Blogや、Webinarやチュートリアル動画を掲載しているAppcelerator University、そしてMediumに投稿されたTitanium関連の記事をピックアップしているAll Titaniumというコーナーがあります。
以前あったQ&Aフォーラムについては、Stack Overflow上でサポートに移行したそうです。
Newest 'appcelerator' Questions - Stack Overflow
投稿する際は appcelerator
タグを付けておくと、Appceleratorの人も見てくれているようです。
ただ上記は英語のサイトになってしまうので、日本語でサポートが必要な方は Titaniumユーザー会のサポートBBS へ投稿するか、Twitterにハッシュタグ #TitaniumJP を付けて投稿すると、どなたか拾ってくれるかもしれません。
最新のSDK情報
最新のSDK 5.2.0がリリースされていて、3/10の時点で5.2.1のRCも出ています。
SDK 5.2.0で提供される新機能などは、以下のラップアップ記事にある動画が非常にわかりやすいので、サンプルと合わせて見てみると良いと思います。
Titanium Mobile DNPの取り組みについて - DNP山下さん
続いて、会場を提供していただいた大日本印刷株式会社の山下さんから、DNPのTitanium Mobileへの取り組みについて紹介していただきました。
DNPでは、特に2011〜2012年ころ、Titanium meetup TokyoやTitanium mobile 2.0ローンチ記念イベントなどで会場提供などでTitaniumコミュニティ活動を支えてくれていました。
DNP自体もネイティブ以外の開発プラットフォームも幅広く取り入れているということで、そのひとつとしてTitaniumも実践活用されているとのこと。
法人向け業務支援やカスタマイズアプリなど、特にタブレット向けアプリのUI構築などで使っていて、分野としてもサイネージやアンケート、コンシェルジュ、教育など多岐に渡るそう。
最近の事例としては、京都のギャラリーなどで鑑賞補助用のアプリに使っていたり、DNPオリジナルタブレット向けにAndroidホームアプリなどに使っているそうです。
TitaniumでAndroidのホームアプリも作れるというのは知らなかったので、ちょっとやってみたい。
今後は、Titanium×Windowsも視野に入れて研究中ということで、特にWindowsタブレットをターゲットに活用していきたいということでした。
ただ、このあとのWindows開発の発表にもありましたが、SDK 5.2.1時点ではまだまだ使い物にならない状態ということで、前途多難な道のりにはなりそうな感じ。
最近は、特に企業から改まってTitaniumの事例などを耳にすることは少ないので、適材適所を見極めて活用されているところがあるというのを聞けたのは心強いですね。
faster-titanium - @shinoutさん
続いて CureApp の @shinoutさん の発表は、TiShadow/LiveViewを凌ぐ新たな爆速開発ツール「faster-titanium」の紹介。
どういうものかは、GitHubリポジトリのアニメーションGIFを見ていただくとイメージしやすいかと思います。
CureApp/faster-titanium: Accelerate Titanium development
TiShadowやLiveViewは便利ですが、落ちやすかったり、なんだか動かないということが多かったので、LiveViewをベースにしつつ、中身をES6ベースにして徹底的にリファクタリングしたそうで、安定性とReact Native並のリロード速度を実現されたそうです。
現状はiOSでしか動いていませんが、ベースとなるLiveViewがAndroidについてはできているので、同様にできるであろうということと、のちのちはWindowsにも対応していきたいという話でした。
Titaniumの特徴として、各プラットフォーム向けのUIをJavaScriptやAlloyフレームワークなど簡略化された構文で構築できる点にあると思いますが、どうしてもビルドして動作確認という部分に時間がかかってしまいます。この部分がfaster-titaniumで短縮できると、さらに開発効率があがるので、Titaniumの強みがより活かせるツールだと思います。
まだ出来たてということもあり、絶賛フィードバック募集中ということなので、ぜひ使って行きたいと思います。
Titanium x Windows開発 - @flat_8_kikiさん
最後は @flat_8_kikiさん による、TitaniumによるWindowsアプリ開発についての発表。
もはや涙無くしては語れない物語で、メモを取る手も止まってしまうほどでした。
この過酷な闘いについてはQiitaに記録されていますので、ぜひご覧ください。
- Windows10ユニバーサルアプリ(UWP)について調べたことまとめ - Qiita
- TitaniumでWindows10(UWP)アプリを作ってみてわかったこと・フロントエンド編 - Qiita
- Windows版Titanium・UI単位系の挙動調査(px、dp) - Qiita
- Titanium製アプリをWindowsアプリ認定キットでテストする(UWP) - Qiita
- ★続★Windows版Titanium・UI単位系の挙動調査(px、dp) - Qiita
- Titaniumで作ったWindows8.1アプリをWindows10用に変換したい - Qiita
- UWP(Windows10)アプリの単位・スケーリング・リソース素材の仕組み - Qiita
そもそもユニバーサルWindowsアプリ開発自体の情報もまだまだ少ない気がするので、そういった点でも貴重な情報だと思います。
SDK 5.4.xおよび5.5.xあたりで改修されている見込みのようなので、最低限の開発ができるようになるのは、その頃からという感じでしょうか。
まだまだ闘いは始まったばかりということで、ガンガン地雷を踏み抜いてくださる覚悟ということなので、今後のWindows×Titaniumの進展も期待できそうです。
※2016/03/25追記
資料公開していただいたので、追記しました。
おわり
終わってみると、非常に濃い話が多くてもくもくどころじゃなかった会でした。
最近は同じマルチプラットフォーム開発でも、React NativeやMSに買収されたXamarinなどに話題を持って行かれている感がありますが、Titanium自体も着実に進化していて、実績という点では他に負けていない製品だと思います。
そして表に出てきてはいないけど、実は使っているという人もけっこういるようなので、そういった人にもぜひもくもく会などに遊びに来ていただいて、情報交換させてもらえると嬉しいですね。
Google Play Musicにアップロードした楽曲を再ダウンロードする
定額の音楽配信サービスは、Google Play Musicを使っています。
特に邦楽は聴きたいアーティストの作品がないことも多いわけですが、Google Play Musicには、手元の音源をアップロードしておくことで、登録しているデバイスに同期して聴くことができる機能があります。
Google Play ミュージック マネージャで音楽を追加する - Google Play ヘルプ
アップロードは50,000曲までできるということなので、ざっくりアルバム4,000〜5,000枚分くらいと考えても、自分の持っているCD全て入ってしまうくらいアップできます。(ちゃんと数えたことないけど、たぶん500枚くらい?多くても1,000枚はない程度)
それならGoogle Play Music上に自分のライブラリを集約させてしまうことも可能なわけですが、もしそうした場合に気になるのが、アップロードした楽曲を再び手元にダウンロードすることはできるのか?ということ。
これができるのであれば、バックアップとしても使えるので、自分的に使い勝手があがるかもと思い調べてみたところ、ちゃんと?その手段が用意されていました。
設定画面の ライブラリのダウンロード の ダウンロード ボタンを押すと…
おもむろにダウンロードが始まりました。
途中でブラウザを閉じるなどしても、またログインするとダウンロードが再開されるようで、進捗状況は左下に表示されています。
ダウンロードされる場所は、設定画面(スクリーンショット一枚目)にある ダウンロードフォルダ で指定できます。
個別ダウンロードはできない
残念ながら、今のところアップロードした楽曲を個別にダウンロードする手段はなさそうです。
もし50,000曲をアップロードしていたと仮定すると、1曲5MBとしても250GBにもなってしまうので、これを一括ダウンロードしかないとなると不便。
とは言っても、それだけの曲数をアップロードするような頃には何かしら改善されていそうな気もしますし、それまで使い続けているかもわからないので、今のところは問題なし。
【国内正規品】Beats by Dr.Dre Mixr 密閉型オンイヤーヘッドホン ホワイト BT ON MIXR WHT
- 出版社/メーカー: beats by dr.dre
- メディア: エレクトロニクス
- 購入: 1人 クリック: 1回
- この商品を含むブログを見る
Alloy Modelの学習・その4(REST API)の続き
前回、REST APIのData Bindingを使ってみたのですが、
そのときに課題として残していたエラーハンドリングなどレスポンスに対する処理に関してと、開発中にAPIエンドポイントを分離したい場合の方法についてメモ。
レスポンスに対する処理
napp.alloy.adapter.restapi を使う際の、エラー処理を含むレスポンスの処理方法を調べてみました。
napp.alloy.adapter.restapiのリポジトリに掲載されている例では引数を受け取っていませんでしたが、各メソッドでは、以下のように success
と error
のコールバックを受け取ることができます。
function doOpen() { memos.fetch({ success : function(models, response){ Ti.API.debug('memo fetch() - success = ' + models + ' / ' + response); }, error : function(models, response){ Ti.API.debug('memo fetch() - error = ' + models + ' / ' + response); } }); }
各 success
と error
コールバックは、サーバーからのレスポンスのHTTPステータスコードによって判断されて呼びだされるため、基本的に意識する必要はありません。
受け取ったモデルの加工だったりエラーに対する処理のほか、通信中のローディング画面の制御などもここでハンドリングできますね。
コールバックの形
操作対象がCollectionなのかModelなのかによって、コールバックには大きく2種類の形があるようです。
メソッド | コールバック | コールバックの形 |
---|---|---|
Collection.fetch() | success error |
function(models, response) |
Model.save() Model.destroy() |
success error |
function(model, response) |
各コールバックの第1引数は、主に操作したモデルデータを受け取るようです。
次に、共通している response
には、Titanium.Network.HTTPClientの responseText
が入ってくるようです。通信をJSONでやりとりする場合は、必要に応じて JSON.parse()
するなどして扱うことになると思います。
コールバックの形を見るに、 responseText
以外の情報は受け取っていないようなので、例えばもしアプリ側でもHTTPステータスコードが必要な場合は、あらかじめレスポンスボディに含めるなどする必要がありそうです。
iOSとAndroidでエンドポイントを分ける
特にPCローカルのサーバーと、iOSとAndroidのシミュレータ/エミュレータで通信確認をする場合のメモです。
iOSのシミュレータでは 127.0.0.1
で開発しているMac側で立ち上げているAlloyModelStudyRestStubにアクセスできるのですが、AndroidのエミュレータやGenymotionの場合、 127.0.0.1
は端末自体を示すらしく、 10.0.2.2
か 10.0.3.2
といったIPになるようです。
モデルの URL
を書き換えれば対応できますが、その都度実施するのも面倒なので、あらかじめ config.json に設定しておき、そのURLを使うようにしました。
app/config.json
{ ... "os:android env:development": { "API_URL": "http://10.0.3.2:4321/memos" }, "os:ios env:development": { "API_URL": "http://127.0.0.1:4321/memos" }, ... }
config.json で設定できる値は、 os:android
や os:ios
といったプラットフォームをあらわすオブジェクトに、動作環境をあらわす env:development
などを組み合わせることで、「Androidのエミュレータの場合」「iOSのエミュレータの場合」に使う値、というようにバリエーションをつけることができます。
それをモデルの中で参照することで、環境ごとに異なるURLを使えるようになりました。
app/models/memo.js
exports.definition = { config: { columns: { "id": "integer", "contents": "text", "priority": "text" }, adapter: { type: "restapi", collection_name: "memo", "idAttribute": "id" }, "URL": Alloy.CFG.API_URL, // <== config.jsonに定義したURL "debug": 1 }, ... };
env:production
などと組み合わせれば、本番環境向けビルドで使うURLも設定できます。
なお、以前はモデルの中でグローバルな Alloy
オブジェクトを参照できなかったので、こちらの記事( AlloyのModelでREST APIからデータを取得する - Qiita )のように一手間必要だったようですが、Alloy 1.4.0?あたりから参照できるようになったようです。
Backbone.js的な対処方法
モデル側のURLの指定を変更する方法とは別に、Backbone.js的に、モデル操作時にオプションとしてURLを渡すという対処方法もあります。
その場合は、 Collection.fetch({url: <url>})
・ Model.save(<params>, {url: <url>})
・ Model.destroy({url: <url>})
といったあたりのメソッドを使えば良いようです。
エンドポイントを動的に変更するようなケースがあれば、使いみちがあるかもしれません。
まとめ
APIのレスポンスに関しては、自前で用意するAPIであれば設計段階で調整できますが、既成サービスのものなどを使う場合はいじりようがないので、実戦使用するときに、また色々と検証しようと思います。
Appcelerator Titanium Smartphone App Development Cookbook - Second Edition
- 作者: Jason Kneen
- 出版社/メーカー: Packt Publishing
- 発売日: 2015/11/30
- メディア: Kindle版
- この商品を含むブログを見る
Alloy Modelの学習・その4(REST API)
引き続き、Alloy Modelを勉強中。
クロスプラットフォームなUIを素早く構築しつつWeb APIと連携するというのは、Titaniumが活用できるパターンだと思います。
というわけで、今回はREST APIとのData Bindingを試してみました。
REST API Sync Adapter
標準で用意されているSync Adapterは、SQLite用のSql AdapterとTitanium.App.Propertiesを使うProperties Adapterの2種類しかありませんが、Sync Adapterは自作することもできます。
Custom Sync Adapters - Alloy Sync Adapters and Migrations
REST API用のSync Adapterを作ってくれている人がいますので、これを採用することにします。
viezel/napp.alloy.adapter.restapi
今回作るもの
アプリ自体は簡単にするため、 その2 で作ったものと同じ仕様とします。
それとは別に、連携先のAPIが必要です。
適当なWeb APIを使っても良かったのですが、CRUDを一通り触りたかったのと、サーバー側に渡ってくるリクエストの内容も把握したかったので、今回はスタブAPIサーバーを立てることにしました。
スタブAPIサーバー
スタブAPIサーバーについては、シンプルで使いやすそうだったMockyを使ってみることにしました。
okv/mocky: http mocking server with simple config written on nodejs
テーブル
スタブなので実際のデータベースは用意しませんが、 その2 と同じ仕様ということで、以下のようなテーブル構造を扱うAPIを用意します。
内容 | カラム | 型 |
---|---|---|
レコードの識別子 | id | INTEGER |
メモの内容 | contents | TEXT |
メモの優先度 | priority | TEXT |
API
上記のテーブルをもとに、CRUDをひととおり呼び出せるよう、以下のようなAPIにすることにしました。
操作 | Method | URL |
---|---|---|
メモを読み込む | GET | http://127.0.0.1:4321/memos |
メモを追加 | POST | http://127.0.0.1:4321/memos |
メモの内容を更新 | PUT | http://127.0.0.1:4321/memos/{ID} |
メモを削除 | DELETE | http://127.0.0.1:4321/memos/{ID} |
スタブAPIPサーバー自体の実装は省略しますが、ダミーデータをメモリ上に保持しておいて、APIの呼び出しに合わせてダミーデータを操作しています。
例えばメモの読み込みAPIを叩くと、こんな感じにJSONのレスポンスを得られる感じです。
データベースを使っていないので、サーバーを再起動するとデータは初期状態に戻ります。
ソースは umi-uyura/AlloyModelStudyRestStub にありますので、こちらをご覧ください。
Qiitaにあった mocky を使ってちょっと賢いスタブAPIサーバを作る - Qiita や Node.js の mocky を使用し スタブREST API を作成してみる、その1 - Qiita あたりを読めば簡単に作れました。
アプリ
アプリ側のソースは umi-uyura/AlloyModelStudyRestApi です。
プロジェクト作成
毎度おなじみCLIでプロジェクト作成。
$ titanium create --type app --id com.example.titanium.alloymodelstudyrestapi --name AlloyModelStudyRestApi --platforms iphone,android --url http://www.example.com --workspace-dir . $ alloy new AlloyModelStudyRestApi
これをベースに、今回もUIはJade & Stylusに、FokkeZB/UTiL/xp.ui を使っています。
REST API Sync Adapter (napp.alloy.adapter.restapi) の準備
GitHubのリポジトリから restapi.js をダウンロードして、プロジェクト内の app/assets/alloy/sync/
へ配置しておきます。
モデル作成
先の想定テーブル構造から、ベースとなるモデルを生成します。このとき、 restapi
タイプというのは Alloy
コマンドがサポートしていないため、いったん sql
として生成しました。
$ alloy generate model memo sql 'id:integer' contents:text priority:text
生成されたモデルファイルをもとに、REST API用に編集します。
exports.definition = { config: { columns: { "id": "integer", "contents": "text", "priority": "text" }, adapter: { type: "restapi", collection_name: "memo", "idAttribute": "id" }, "URL": "http://127.0.0.1:4321/memos", "debug": 1 }, extendModel: function(Model) { _.extend(Model.prototype, { }); return Model; }, extendCollection: function(Collection) { _.extend(Collection.prototype, { comparator: function(data) { return (0 - data.get('priority').length); } }); return Collection; } };
編集した箇所としては、以下のとおりです。
config.adapter.type
をrestapi
に変更URL
を追加し、スタブAPIのURLを設定debug
を追加、これでAPIを使う際のリクエスト/レスポンスがデバッグ出力されてわかりやすい
他に headers
や parentNode
をといった設定もありますが、今回は未使用。
以下はデバッグ出力の例。
Data Binding
ビューの部分は 前回 と同じもので、コントローラもほぼ一緒で動きました。
一箇所修正したのは、メモを追加したあとに呼び出していた memos.fetch()
の部分で、通信が発生してタイミングが変わるせいか、これを呼び出してしまうと追加したはずのメモが消えてしまう現象が発生しました。
その上の行の memos.add(m)
までで、ListViewには新しいメモが追加されていたので、 memos.fetch()
は削除することにしました。
app/controllers/index.js
... function addText() { var txt = $.memoText.getValue(); var params = { contents: txt, priority: '' }; var m = Alloy.createModel('memo', params); m.save(); memos.add(m); //memos.fetch(); <== 削除した $.memoText.setValue(''); } ...
エラーハンドリングについて
今回やっていないこととして、通信のエラーハンドリングがあります。
データ構造を同じにしたこともありますが、SQL用からREST API用にAdapterを入れ替えて、ほぼそのまま動かせてしまいました。
しかし、ローカルにあるデータベースなどと比べて、インターネットを介した通信は不安定だったり、APIサーバー側で何らかの問題が発生することなども考えられます。
そのため、napp.alloy.adapter.restapiには、以下のような感じで通信成功時とエラー時で処理をハンドリングできるようになっています。
var collection = Alloy.createCollection("MyCollection"); //or model //the fetch method is an async call to the remote REST API. collection.fetch({ success : function(){ _.each(collection.models, function(element, index, list){ // We are looping through the returned models from the remote REST API // Implement your custom logic here }); }, error : function(){ Ti.API.error("hmm - this is not good!"); } });
napp.alloy.adapter.restapiを使ってきちんと実装する場合は、この点も考慮する必要があると思います。
参考
- viezel/napp.alloy.adapter.restapi
- AlloyのModelでREST APIからデータを取得する - Qiita
- Titanium + Alloy + napp.alloy.adapter.restapiで作る簡単Qiitaビューワーアプリ - Qiita
- Titanium + Alloy + napp.alloy.adapter.restapiで作る簡単Qiitaビューワーアプリ応用編(ページネーション機能の実装) - Qiita
モックサーバー
- okv/mocky: http mocking server with simple config written on nodejs
- mocky を使ってちょっと賢いスタブAPIサーバを作る - Qiita
- Node.js の mocky を使用し スタブREST API を作成してみる、その1 - Qiita
- 【図解】RESTful WebサービスにおけるHTTPステータスコード : アジャイル株式会社
Appcelerator Titanium Smartphone App Development Cookbook - Second Edition
- 作者: Jason Kneen
- 出版社/メーカー: Packt Publishing
- 発売日: 2015/11/30
- メディア: Kindle版
- この商品を含むブログを見る