appengineでの開発

3,319 views
3,286 views

Published on

Published in: Technology
0 Comments
5 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
3,319
On SlideShare
0
From Embeds
0
Number of Embeds
204
Actions
Shares
0
Downloads
11
Comments
0
Likes
5
Embeds 0
No embeds

No notes for slide

appengineでの開発

  1. 1. appengine での開発 @najeira
  2. 2. どんなもの? http://labola.jp/ いわゆる SNS スポーツを見る人、やる人で交流 <ul><li>日記や観戦記
  3. 3. 施設のレビュー
  4. 4. 対戦相手の募集 </li></ul>などなど
  5. 5. 採用の経緯 サービスのリニューアルを行うことに ⇒ 旧システムの拡張が難しい   ⇒ フルリニューアル 1 から作るので、選択肢として Google App Engine も候補にできた。 移植はオススメできない
  6. 6. 採用の経緯 性能要件 1 億 PV/ 月 <ul><li>サーバが多数必要になる
  7. 7. DB のパーティショニングも必要かも </li></ul>しかし短期間でリニューアルしたい Google App Engine は 自動 スケールアウト
  8. 8. LAMP は? 「スケールアップ」も、かなりのもの。 ハードの性能向上 <ul><li>マルチコア CPU
  9. 9. メモリ 48GB
  10. 10. SSD </li></ul>
  11. 11. LAMP は? メモリ 48GB ⇒ コミュニティなのでデータが多い  ⇒いずれメモリに乗らなくなる SSD ⇒ RDB が対応しきれていない?
  12. 12. 問題 <ul><li>セキュリティポリシー </li></ul> ⇒ Google なら大丈夫だろう <ul><li>Availability </li></ul> ⇒ 99.9% (月平均 40 分)くらい?    ⇒先月くらいから調子悪い? <ul><li>技術的な問題 </li></ul> ⇒ たいしたことではない
  13. 13. 利点 自動 でスケールアウトする <ul><li>インフラは Google が面倒を見てくれる
  14. 14. 障害対応は Google がやってくれる </li></ul>⇒ インフラ担当を置くコストが 削減 ⇒ アプリの開発に 集中 できる
  15. 15. 経緯、利点、欠点  質問・議論?
  16. 16. 距離が遠い アメリカって遠い……! appengine 往復 200ms
  17. 17. 静的リソースを別サーバ リソースサーバを国内 リソース サーバ appengine www.example.jp img.example.jp
  18. 18. プロキシを使う プロキシ appengine 往復 20ms 往復 200ms
  19. 19. プロキシの利点 <ul><li>静的なファイルの配信が高速
  20. 20. プロキシでキャッシュが出来る
  21. 21. エラーハンドリングが出来る
  22. 22. ネイキッドドメインが使える
  23. 23. 独自ドメインでの SSL が使える </li></ul>
  24. 24. プロキシの欠点 <ul><li>サーバが必要
  25. 25. プロキシが障害点になる </li></ul>
  26. 26. その他の CDN Google Code ⇒ 100ms?  利用規約的には? Amazon Cloud Front ⇒ 速い。値段は高い。 Akamai ⇒ 速い。値段は超高い。
  27. 27. 次善の策 HTTP リクエストを減らす <ul><li>CSS や JS は 1 ファイルに結合
  28. 28. 画像はまとめて CSS スプライト
  29. 29. HTML に CSS と JS を埋め込む
  30. 30. 静的リソースには長いキャッシュ時間 </li></ul> ⇒ 更新したら URL を変えれば良い    src=&quot;/main.css?20100604&quot;
  31. 31. 開発環境でもプロキシ Python のローカルサーバ はシングルスレッド 画像・ CSS ・ JS が多いとエラーが出る ローカルでも Apache などでリバースプロキシ ログ画面からもノイズが減る プロキシ dev_appserver
  32. 32. プロキシについて  質問・議論?
  33. 33. Datastore データストアをおさえれば Google App Engine は怖くない 単純な Key-Value Store よりも高機能
  34. 34. Datastore JOIN できない ⇒ 正規化しすぎない(冗長に持つ) ⇒ データ更新時にがんばる 個人的な指針 <ul><li>検索で使うプロパティは冗長に持つ </li></ul>
  35. 35. 正規化しない class Univ(db.Model): category = db.StringProperty() ... class Student(db.Model): univ = db.ReferenceProperty(Univ) univ_category = db.StringProperty() ... #Student に Univ のプロパティをコピー student = Student ( univ = univ, univ_category=univ.category ) student .put()
  36. 36. 正規化しない #Univ の category で Student を検索 q = Student.all() q.filter( 'univ_category =' , 'national' ) students = q.fetch(10)
  37. 37. Datastore トランザクションに制約がある ⇒ タスクキューを使う ⇒ Java なら slim3 のグローバルトランザクション
  38. 38. Datastore 集計関数がない ⇒ データ更新時にがんばる
  39. 39. その他の制約 リクエストを 30 秒以内に処理しないとダメ ⇒ Google App Engine でなくても当然 ⇒ 原則として 1 秒以内で処理しよう  ⇒スケールアウトの条件?
  40. 40. Quota の傾向 課金のほとんどは CPU CPU の多くは Datastore ⇒ ここのチューニングは重要 実データ量と同じくらいの メタデータ ⇒ でも安い
  41. 41. RPC を減らす # ループで ReferenceProperty 参照は NG for student in students: print student.univ.name # RPC(single get) #Key のリストで db.get しよう! keys = [] for student in students: keys.append(getattr(student.__class__, 'univ').get_value_for_datastore(student)) univs = db.get(keys) # RPC(batch get) for univ in univs: print univ.name
  42. 42. RPC を減らす # キャッシュを使う cache = memcache.get(name) if cache: return cache # キャッシュが無ければ通常処理 students = ... # RPC html = template.render( ' example .html', students = students ) memcache.set(name, html) return html キャッシュは出力に近いところ (HTML)
  43. 43. batch put #put もまとめて行う for student in students: student.age = ... # 更新処理 #student.put() # ループ内で RPC しない db.put(students) #batch put # 一度の RPC は 1MB という制約あり
  44. 44. keys_only #keys_only だと速い q = Student.all(keys_only=True) q.filter( ... ) keys = q.fetch(1000)
  45. 45. ページング class Diary(db.Model): #created_at = db.DateTimeProperty(...) created_id = db.StringProperty() ... diary = Diary(...) diary.created_id = '%s|%s' % ( jst_now(), rand_str(len=10)) diary.put()
  46. 46. ページング # 先頭ページ q = Diary.all() q.order('-created_id') entities = q.fetch(10 + 1) diaries = entities[:10] if 10 < len(entities): next = entities[-1] else: next = None
  47. 47. ページング # next の次からクエリ q = Diary.all() q.order('-created_id') q.filter('-created_id <=', next.created_id) entities = q.fetch(10 + 1)
  48. 48. ページング Google App Engine のドキュメント http://code.google.com/intl/ja/appengine/articles/paging.html
  49. 49. Datastore など  質問・議論?

×