サーバーからiOSアプリを変更する

6,096 views
5,952 views

Published on

2014/4/26のyidev@恵比寿で発表したスライドです。

Published in: Engineering
0 Comments
10 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
6,096
On SlideShare
0
From Embeds
0
Number of Embeds
4,085
Actions
Shares
0
Downloads
11
Comments
0
Likes
10
Embeds 0
No embeds

No notes for slide

サーバーからiOSアプリを変更する

  1. 1. サーバーからiOSアプリを変更する 2014/4/26 @TachibanaKaoru
  2. 2. 自己紹介 • @TachibanaKaoru • 渋谷のgenesixで働くiOSエンジニアです • Blog : http://www.toyship.org/
  3. 3. サーバーからiOSアプリを変更する • 一回リリースしたiOSアプリをサーバーサイドで変更し たい • できるだけ頻繁にアプリの仕様やUIを変更したい • ユーザーによって表示するUIを変えて、A/Bテストを 行いたい
  4. 4. MVC in server/local Model Controller View Native Code (Objc..) Server API Storyboard or Xib or Code
  5. 5. UIWebViewを使う • よく使われるのがUIWebViewで画面を作成し、表示内 容をすべてサーバーサイドで作成する • Model/View/Controlの処理の大部分がサーバー側となる ため迅速な変更ができるが、いろいろと弊害がある
  6. 6. UIWebViewによる弊害 • 全体的なパフォーマンス • 特にTableViewではUIKitのCellのresuseの仕組みが使 えないため、操作が遅くなる • 多量のデータハンドリングに問題あり • デバイス固有の機能を使うには制限がある
  7. 7. UIWebViewを使わずに動的に変更するには • 簡単な例としては、UIに表示する画像の一部をサー バーサイドからもってくる方法もありますが… • 実施例:アプリ起動時の「ようこそ画面」をサーバー サイドから取得し、ABテストを実施 • ただ、この仕組みをコードに記述する必要があるため、 コードに仕組みをいれこまないような形にしたい • もっと大幅な変更を動的に行いたい
  8. 8. Storyboardをネットワークからダウンロード • @tokoromさんの案 • http://www.slideshare.net/yutatokoro7/potatotips1 • StoryboardをNSBundleに含めてzipにして、サーバー に置いておく • アプリがダウンロードしてunzipしてStoryboardを作 成する
  9. 9. MVC in server/local Controller View Server API Model Storyboardをダウンロード することで、この部分が サーバーで更新できるよう になる Storyboard or Xib Native Code (Objc..)
  10. 10. Storyboardをネットワークからダウンロード • Storyboardが変更可能な場合、画面レイアウトなどの 要素は動的に変更変更することが可能になる • しかし、ModelとViewの両方をサーバーサイドにして も、Modelを変更してViewに反映させるためには、 Controllerの変更が必要になる
  11. 11. 例えば…… 今まで表示していなかったTweetのFavorite数を タイムライン上に表示するようにしよう! ここのTweetボタンのアイコンの画像を変更しよう OK! NG!
  12. 12. Modelの変更に対して、Controlを変更せずに、 サーバーサイドだけでで対応させたい!
  13. 13. 対応例 • 今まで別のものを表示していたTableViewに、このjson のなかの特定の要素を表示するという変更に、 Storyboardだけで対応してみたいと思います。 • http://itunes.apple.com/jp/rss/topfreeapplications/limit=20/json { "feed": { "author": { "name": { "label": "iTunes Store" }, "uri": { "label": "http://www.apple.com/jp/itunes/" } }, "entry": [ { "category": { "attributes": { "im:id": "6016", "label": "エンターテインメント", "scheme": "https://itunes.apple.com/jp/genre/ios-entateinmento/id6016?mt=8&uo=2", "term": "Entertainment" }
  14. 14. 独自UITableViewControllerの設定
  15. 15. • このUITableViewControllerクラスは、CallすべきAPIの EndPointのURL、表示すべきJsonの要素名をpropertyと して持っています。 ! • 通常、このpropertyの代入は、ソースコード上で行って いますが……。 独自UITableViewControllerの設定 @interface CommonListViewController : UITableViewController @property (nonatomic,strong)NSString* strField; @property (nonatomic,strong)NSString* strEndPoint; @property (nonatomic,strong)NSArray* items; @end self.EndPoint = @“http://itunes.apple.com/jp/rss/topfreeapplications/limit=20/json”; self.strField = @“feed.entry”;
  16. 16. 独自UITableViewControllerの設定 StoryboardのUser Defined Runtime Attributesを使い、ソースコード 上でなく、StoryboardでstrEndPoint、strField の値を入力します。
  17. 17. 独自UITableViewControllerの設定 - (void)viewWillAppear:(BOOL)animated{ [super viewWillAppear:animated]; ! NSURL *url = [NSURL URLWithString:self.strEndPoint]; NSURLRequest *request = [NSURLRequest requestWithURL:url]; [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:^(NSURLResponse *response, NSData *data, NSErro *error) { NSDictionary *jsonDictionary = [NSJSONSerialization JSONObjectWithData:data options: error:nil]; self.items = [jsonDictionary valueForKeyPath:self.strField]; [self.tableView reloadData]; }]; } Storyboardで設定されたstrEndPointの値 Storyboardで設定されたstrFieldの値
  18. 18. 独自UILabelの設定 StoryboardでUIEntityLabelのstrEntityプロパティに、そのラベ ルに表示したい要素名を指定する @interface UIEntityLabel : UILabel @property(nonatomic,strong)NSString* strEntity; ! @end
  19. 19. 独自UILabelの設定 - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { //(いつもの処理) NSDictionary* dict = [self.items objectAtIndex:indexPath.row]; NSArray* cellSubviews = cell.contentView.subviews; for( UIView* control in cellSubviews){ if( [[[control class] description] isEqualToString:@"UIEntityLabel"]){ UIEntityLabel* label = (UIEntityLabel*)control; NSString* strData = [dict valueForKeyPath:label.strEntity]; label.text = strData; ! } } return cell; }
  20. 20. 実行結果 Storyboardで指定したEndpointのAPIをよび、 Storyboardで指定した要素を表示することが できる
  21. 21. MVC in server/local Controller View storyboard from server ModelServer API Native Code (Objc..)
  22. 22. UIViewControllerの場合 • 基底クラスがUIViewControllerの場合にも、 UITableViewControllerと同様に独自ラベル (UIEntityLabel)とUser Defined Runtime Attributeの仕 組みを使えばなことが可能です。
  23. 23. まとめ • StoryboardとUser Defined Runtime Attributeをうまく使 うと、サーバーサイドだけでModel/Viewの大幅な変更 ができるようになります。

×