Obj-C再入門・というかCocoa?のNSURLConnection関連のハマりどころ

ObjCというよりもCocoaのAPIの使い方だけど、ここ2日間、ハマっていたのがようやく解決。解決してみると、実にくだらないバグ。

あるデータをwebサーバにアップロードするために、以下のようなコードを書いた。

NSURLConnection *con = [[NSURLConnection alloc] initWithRequest:req delegate:self]; //(1)
[con start];  //(2)

ふんふん、(1)コネクションを作って、(2)通信を開始してるのね、と思うかもしれない。実際俺はそう思い込んでた。しかし上記のコードは非常にまずい。

実は(1)のinitWithRequest:delegateメッセージ呼び出しの時点で、通信は開始しているのだ!なので(1)の実行後に(2)を実行すると、通信が始まってるのに、再び通信を開始しようとする。それで「EXEC_BAD_ACCESS」なんて言われて、iPhoneが落ちるはめになる。

ちなみに、コネクションを作るにはもうひとつinitWithRequest:delegate:startImmediately:というメッセージが用意されていて、3つ目のメッセージにNOを与えると、通信はせず、コネクションだけ作ることが可能。で、そのコネクションの通信を開始するためのメッセージが、上記のstartだった、というわけ。


いや、まあドキュメントをちゃんと読めばわかるんだけどさ、、「initWithRequest」っていわれると、普通はコネクションを初期化するだけに見えると思うんだけど..通信まで始めちゃうのね・・。せめてinitAndBeginWithRequestみたいな名前にしてくれると、こんなヘンなところでハマることもなかったんだがねぇ。。しかもエラーメッセージも「EXEC_BAD_ACCESS」だけだし....orz

ちなみに今回のハマリは、以下のやり取りのおかげで解決できました。
http://www.cocoabuilder.com/archive/message/cocoa/2009/1/6/226801

みなさんもお気をつけ下さい。。。