読者です 読者をやめる 読者になる 読者になる

ありがとう。また会おう。

まぁゆるりとやっていきますよと。

「これは罠。PHPでiPhone端末にPUSH通知を送る際の落とし穴」は(一部)罠

最近、今更ながら「数学ガール」にハマっていて、ゲーデル不完全性定理の自己言及っぽい釣りタイトルにしてみました(^_^;)
大学、大学院と数学やってましたけど、
もう数学勉強しなくなってずいぶんたつしキツイかなと思ったんですが
三つ子の魂百までというか、昔取った杵柄というか、読み始めれば以外とすっと入っていけました。
もちろんこの本の構成のうまさと物語の面白さもあると思うんですけどね。おすすめの本です。

という前置きはさておき。
業務でiOS のPUSH通知を扱うことになり、いろいろと調べてていきついた記事が

これは罠。PHPiPhone端末にPUSH通知を送る際の落とし穴 | 株式会社LIG
http://liginc.co.jp/programmer/archives/2355

これだったんですが。
1年以上前のエントリーなので、もしかしたら当時とは状況違うのかも、というところも前置きしつつ。
自分がさらに色々調べた感じ、このエントリーにある

1回の通信で全パケットが5000〜7000バイトを超えるとAPNSから切断される

については、どうやらそのような制限はないのでは、という結論に至りました。

実際、この記事についているブクマコメントやTwitterをみると、少数ながら懐疑的な意見もあった模様。
ただ、それ以上に記事を鵜呑みにして拡散しているものも多く、実際google検索でも上位にヒットするので
ちゃんと真偽を確かめたほうがいいのでは、と思い、この記事を書くに至りました。

で、詳しい数値は一般公開ブログなので記載は控えますが、
ここに書かれてる数字よりかはかなり長いバイト長のパケットを送っても、
現状APNSから切断されるという事象は確認していません。

ただ、じゃあ無制限にゴンゴン送れるのかというと、それもそうでもないようで
このエントリーにも記載されているPHP実装の有名なライブラリ「ApnsPHP」GitHubのIssueにこんな書き込みが。

ApnsPHP too fast for apns · Issue #2 · duccio/ApnsPHP · GitHub
https://github.com/duccio/ApnsPHP/issues/2

要約すると、
「あまりにも速く送りすぎるとどうもエラーになるんで、
1メッセージあたり50ミリ秒くらいインターバルおいたらうまくいくみたい」
というところ。
斜め読みならぬ斜め翻訳なので間違ってたらごめんなさい。。。

で、実際、ApnsPHPの実装も、2012年10月29日の修正で、デフォルトで1メッセージ送ったあとに10ミリ秒sleep入れるようになっていました。
また、上にあげたIssueのコメントに、Apple公式ドキュメントからの引用があり、そこでは
少なくとも秒間9000メッセージは送れるよ、とあります。
この数値から逆算すると、1メッセージあたり10〜50ミリ秒おいた方がいい、てのもそうなのかなという気がする数字。
計算上は約110マイクロ秒くらいでよさそうだが、多少余裕をみているのだろうと思います。

なお、元記事のフルスクラッチのコードでは、5000バイト送るごとに一旦コネクション閉じて再度開く、みたいなことをしていますが
この部分は、PUSH通知送る件数が多いと、パフォーマンスかなり悪くなる要因になると思います。
なので、現時点は、素直にApnsPHPに任せたほうがいいかと思います。