2014年8月アーカイブ

あまり褒めらた方法ではないのですが、処理を簡単にするためAFNetworkingでの通信を同期で行いたいことはありますよね。

AFNetworkingのNSOperationQueuewaitUntilAllOperationsAreFinishedを呼んでやればできるのかとおもいきや、どうも意味が違うらしい。

そこで簡単に思いつくGCDのSemaphoreを使ってコールバックが終わるまで待つようにしてみたところ...

client.getのところで実行がデッドロックしているようでコールバックブロックが呼ばれません。

APIのログを確認するとサーバにアクセスは来ています。

これ、結構ハマってしまい諦めて別の方法で実装しようかなと思ってたのですが「Are AFNetworking success/failure blocks invoked on the main thread?」を発見してcompletionQueueの存在を知ります。

たぶんここcompletionQueueが設定されていない場合、dispatch_get_main_queue()が使われるのでデッドロックするのだと思われます。

dispatch_get_global_queueとかdispatch_queue_createとかしたものをセットすれば良さそうです。

先ほどのRubyMotionのafmotionを介して実行したサンプルですとAFMotion::Client.buildのDSLブロックに

   :
  response_serializer :json
  completion_queue Dispatch::Queue.concurrent
end

とかできれば良かったのですが、ClientDSLクラスには定義されてないようです。(プルリクチャンスかw) ただ返されるclientAFHTTPRequestOperationManagerそのもののようなので使う前に設定してみます。

client.completionQueue = Dispatch::Queue.concurrent

EXC_BAD_ACCESSります。RubyMotionのDispatch::Queueオブジェクトは元のGCDオブジェクトそのものではないので当然か。Dispatch::Queue.concurrent.methodsでメソッドを見てみるとdispatch_objectなんてものがありますので、おそらくコレですね。

期待通りに動くようになりました( ˘ω˘)

このアーカイブについて

このページには、2014年8月に書かれたブログ記事が新しい順に公開されています。

前のアーカイブは2013年9月です。

次のアーカイブは2015年4月です。

最近のコンテンツはインデックスページで見られます。過去に書かれたものはアーカイブのページで見られます。

最近のブログ記事

Amazon