{“errors”:[{“code”:215,“message”:“Bad Authentication data.”}]}
完整错误日志是:
E restkit.network:RKObjectRequestOperation.m:297 Object request Failed: Underlying HTTP request operation Failed with error: Error Domain=org.restkit.RestKit.ErrorDomain Code=-1011 "Expected status code in (200-299),got 400" UserInfo=0x1780f6f80 {NSLocalizedRecoverySuggestion={"errors":[{"code":215,"message":"Bad Authentication data."}]},NSErrorFailingURLKey=https://api.twitter.com/1.1/statuses/user_timeline.json?user_id=3116882322&count=2&screen_name=ann_10p,AFNetworkingOperationFailingURLRequestErrorKey=<NSMutableuRLRequest: 0x178202740> { URL: https://api.twitter.com/1.1/statuses/user_timeline.json?user_id=3116882322&count=2&screen_name=ann_10p },AFNetworkingOperationFailingURLResponseErrorKey=<NSHTTPURLResponse: 0x1702271e0> { URL: https://api.twitter.com/1.1/statuses/user_timeline.json?user_id=3116882322&count=2&screen_name=ann_10p } { status code: 400,headers { "content-encoding" = gzip; "Content-Length" = 87; "Content-Type" = "application/json;charset=utf-8"; Date = "Wed,01 Apr 2015 09:46:42 GMT"; Server = "tsa_a"; "Strict-Transport-Security" = "max-age=631138519"; "x-connection-hash" = 4c123a59a023cd86b2e9a3e9fc84cd7b; "x-response-time" = 4; } },NSLocalizedDescription=Expected status code in (200-299),got 400} 2015-04-01 14:47:13.223 TwitterIntegration[1086:60b] I restkit.network:RKHTTPRequestOperation.m:154 GET 'https://api.twitter.com/1.1/statuses/user_timeline.json?user_id=3116882322&count=2&screen_name=ann_10p' 2015-04-01 14:47:13.225 TwitterIntegration[1086:60b] E restkit.network:RKHTTPRequestOperation.m:178 GET 'https://api.twitter.com/1.1/statuses/user_timeline.json?user_id=3116882322&count=2&screen_name=ann_10p' (400 Bad Request) [0.0013 s]: Error Domain=org.restkit.RestKit.ErrorDomain Code=-1011 "Expected status code in (200-299),got 400}
码:
- (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view,typically from a nib. [self addLoginButton]; } -(void) addLoginButton { TWTRLogInButton *logInButton = [TWTRLogInButton buttonWithLogInCompletion:^(TWTRSession *session,NSError *error) { // play with Twitter session if(session) { NSLog(@"logged in success! with session : %@",session); [Global sharedInstance].session = session; [self requestUserTimeline]; } else { NSLog(@"session is null"); } }]; logInButton.center = self.view.center; [self.view addSubview:logInButton]; } -(void) requestUserTimeline { RKObjectMapping *mapping = [RKObjectMapping mappingForClass:[UserTimeline class]]; [mapping addAttributeMappingsFromDictionary:@{ @"text": @"tweetText",@"favorited": @"favourited",@"created_at": @"createdAt",@"user.name": @"name",@"id": @"tweetID",@"user.profile_image_url": @"profileImageURL" }]; NSIndexSet *statusCodes = RKStatusCodeIndexSetForClass(RKStatusCodeClassSuccessful); // Anything in 2xx RKResponseDescriptor *responseDescriptor = [RKResponseDescriptor responseDescriptorWithMapping:mapping pathPattern:nil keyPath:nil statusCodes:statusCodes]; Nsstring *params = [Nsstring stringWithFormat:@"?user_id=3116882322&count=2&screen_name=ann_10p",[Global sharedInstance].session.userID,[Global sharedInstance].session.userName]; NSMutableuRLRequest *request = [NSMutableuRLRequest requestWithURL:[NSURL URLWithString:[@"https://api.twitter.com/1.1/statuses/user_timeline.json" stringByAppendingString:params]]]; [request setHTTPMethod:@"GET"]; RKObjectRequestOperation *operation = [[RKObjectRequestOperation alloc] initWithRequest:request responseDescriptors:@[responseDescriptor]]; [operation setCompletionBlockWithSuccess:^(RKObjectRequestOperation *operation,RKMappingResult *result) { UserTimeline *timeline = [result firstObject]; NSLog(@"Mapped the article: %@",timeline); } failure:^(RKObjectRequestOperation *operation,NSError *error) { NSLog(@"Failed with error: %@",[error localizedDescription]); }]; [operation start]; }
请帮我调试这个问题.谢谢.
解决方法
1)当您第一次成功登录Twitter时,已为用户创建了一个TWTRSession会话.即使您关闭应用程序并重新打开它,它也会持续.
2)如果已经为您创建了会话,并且您尝试登录获取另一个会话对象而不注销,则将返回身份验证错误.
3)您可以使用以下方法检查会话是否存在:
if([[Twitter sharedInstance] session]) { NSLog(@"session already present!!!"); NSLog(@"signed in as %@",[[[Twitter sharedInstance] session] userName]); } else { NSLog(@"you need to login!!"); }
4)我会建议使用登录
[[Twitter sharedInstance] logInWithCompletion:^(TWTRSession * session,NSError * error)];
代替:
[TWTRLogInButton buttonWithLogInCompletion:^(TWTRSession * session,NSError * error)];
Use Twitter’s login button only,when you are sure that no session
exists currently.
5)如果Twitter的身份验证真的取笑你,请卸载该应用程序并尝试全新安装.这是最后的解决方案!
6)要从会话注销,请使用[[Twitter sharedInstance] logout];
编码部分:
我假设您已经按照Fabric mac app执行了所有步骤.
首先登录用户,然后发出时间表请求.
-(void) loginUserToTwitter { if([[Twitter sharedInstance] session]) { NSLog(@"session already present!!!"); NSLog(@"signed in as %@",[[[Twitter sharedInstance] session] userName]); [self getUserTimeline]; } else { NSLog(@"session not found. Make new request!"); [[Twitter sharedInstance] logInWithCompletion:^(TWTRSession *session,NSError *error) { if(error) NSLog(@"error occurred... %@",error.localizedDescription); else { NSLog(@"Successfully logged in with session :%@",session); [self getUserTimeline]; } }]; } } -(void) getUserTimeline { NSURLRequest *request = [[[Twitter sharedInstance] apiclient] URLRequestWithMethod:@"GET" URL:@"https://api.twitter.com/1.1/statuses/user_timeline.json" parameters:@{@"userid": [Twitter sharedInstance].session.userID,@"count" : @"5",@"screen_name" : [Twitter sharedInstance].session.userName} error:nil]; NSURLResponse *response; NSError *error; NSData *data = [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:&error]; if(!data) { NSLog(@"error....: %@",error.localizedDescription); } else { Nsstring *string = [[Nsstring alloc] initWithData:data encoding:NSUTF8StringEncoding]; NSLog(@"%@",string); [twitterResponse removeAllObjects]; NSArray *arrayRep = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableLeaves error:nil]; twitterResponse = [NSMutableArray arrayWithArray:[TWTRTweet tweetsWithJSONArray:arrayRep]]; [_tableView reloadData]; } }
我更喜欢使用Twitter SDK的方法来使用[TWTRTweet tweetsWithJSONArray:arrayRep]而不是Restkit来提取推文.这里的事情真的很容易处理.
在Twitter的标准风格中显示推文:
- (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view,typically from a nib. // Setup tableview self.tableView.estimatedRowHeight = 150; self.tableView.rowHeight = UITableViewAutomaticDimension; // Explicitly set on iOS 8 if using automatic row height calculation self.tableView.allowsSelection = NO; [self.tableView registerClass:[TWTRTweetTableViewCell class] forCellReuseIdentifier:@"TweetCell"]; } #pragma mark - Tableview Methods - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView { return 1; } - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section { return twitterResponse.count; } - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath { static Nsstring *cellID = @"TweetCell"; TWTRTweetTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellID forIndexPath:indexPath]; TWTRTweet *tweet = twitterResponse[indexPath.row]; [cell configureWithTweet:tweet]; return cell; } // Calculate the height of each row. Must to implement - (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath { TWTRTweet *tweet = twitterResponse[indexPath.row]; return [TWTRTweetTableViewCell heightForTweet:tweet width:CGRectGetWidth(self.view.bounds)]; }
注意:
从here下载Fabric SDK.您必须输入电子邮件地址.他们会通过电子邮件向您发送一些下载链接,您必须按照一些步骤操作. Fabric Mac App将让您完全配置xcode项目.
希望能帮助到你!
参考文献:
Twitter Login
Show Tweets
Cannonball Sample Project