下面是一段你将会看到的数据:
2014-01-05 07:42:27.697 TwitterInstant[40308:5403] { "search_metadata" = { "completed_in" = "0.019"; count = 15; "max_id" = 419735546840117248; "max_id_str" = 419735546840117248; "next_results" = "?max_id=419734921599787007&q=asd&include_entities=1"; query = asd; "refresh_url" = "?since_id=419735546840117248&q=asd&include_entities=1"; "since_id" = 0; "since_id_str" = 0; }; statuses = ( { contributors = ""; coordinates = ""; "created_at" = "Sun Jan 05 07:42:07 +0000 2014"; entities = { hashtags = ...?
signalForSearchText:方法还会发送error事件到subscribeNext:error: block里。你最好自己尝试一下。
在模拟中打开设置应用,选择你的Twitter账户,然后按“Delete Account”删除它。
再重新运行应用,现在还是允许访问用户的Twitter账号,但是没有可用的账号。signalForSearchText:会发送一个error,输出如下:
2014-01-05 07:52:11.705 TwitterInstant[41374:1403] An error occurred: Error Domain=TwitterInstant Code=1 "The operation couldn’t be completed. (TwitterInstant error 1.)"?
Code=1表示是RWTwitterInstantErrorNoTwitterAccounts错误。在实际的应用中,你可能需要判断错误码来做一些更有用的事情,而不只是打印到控制台。
这表明了error事件很重要的一点,当signal发送error后,会直接到达处理error的block。这是一个例外流程。
注意:当请求Twitter返回错误时也是一个例外流程,尝试一下,比较简单的方法就是把请求参数改成无效的。
我相信你已经想把搜索Twitter返回的JSON值和UI连接起来了,但是在这之前还有最后一个需要做的事情。现在需要稍微做一些探索,来看一下这到底是什么!
在subscribeNext:error:中如下图所示的地方加一个断点:
重新运行应用。如果需要的话,再次输入Twitter登录信息。在search field中输入一些内容。当在断点停止时,你应该能看到和下图类似的东西:
注意断点停在的代码并没有在主线程,也就是截图中的Thread 1中执行。请记住你只能在主线程中更新UI。因此你需要切换线程来在UI中展示微博的列表。
这展示了ReactiveCocoa框架很重要的一点。上面显示的操作会在signal最开始发送事件的线程中执行。尝试在管道的其他步骤添加断点,你可能会惊奇的发现它们也是在不同线程上执行的。
所以接下来你要怎么更新UI呢?通常的做法是使用操作队列(参见教程如何使用 NSOperations 和 NSOperationQueues)。但是ReactiveCocoa有更简单的解决办法。