I have problem publishing a photo from ios app to facebook page as the page's admin. The only thing I can publish as admin is a status message.
Here what I did.
// get access token first
[FBRequestConnection startWithGraphPath:#"/__facebook_page_id__?fields=access_token" completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
// make sure its not nil
if ([result valueForKey:#"access_token"] != nil) {
NSString *accessToken = [result objectForKey:#"access_token"];
NSLog(#"Access token: %#", accessToken);
NSMutableDictionary* params = [[NSMutableDictionary alloc] init];
[params setObject:#"This is some status message" forKey:#"message"];
[params setObject:accessToken forKey:#"access_token"];
[FBRequestConnection startWithGraphPath:#"/__facebook_page_id__/feed" parameters:params HTTPMethod:#"POST" completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
NSLog(#"Result: %#", result);
NSLog(#"Error: %#", error);
}];
}
}];
The above code successfully publish to facebook page as the admin. Since I need to publish a photo, I need to change the grap path to /facebook_page_id/photos.
NSMutableDictionary* params = [[NSMutableDictionary alloc] init];
[params setObject:UIImagePNGRepresentation(self.imagePreview.image) forKey:#"picture"];
[params setObject:#"This is some description" forKey:#"message"];
[params setObject:accessToken forKey:#"access_token"];
[FBRequestConnection startWithGraphPath:[NSString stringWithFormat:#"/__facebook_page_id__/photos"] parameters:params HTTPMethod:#"POST" completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
NSLog(#"Result: %#", result);
NSLog(#"Error: %#", error);
}];
The above code is successfully published, but not as admin. Eventhough I am using the page's access token.
I thought the path fb_page_id/photos was broken, so I tried to use the fb_page_id/feed and send other fields such as link, picture, etc. But still, it posted as the user, not the page's admin.
Please let me know if I am doing wrong.
Some Information:
- Deployment target: 5.1 and above
- Facebook SDK Version: 3.7
Thank you in advance.
I finally found the answer. Just in case somebody having the same problem, here is what I am doing.
You will need a Page's access_token by accessing /page_id?fields=access_token
[FBRequestConnection startWithGraphPath:[NSString stringWithFormat:#"/%#?fields=access_token", FB_PAGE_ID] completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
// if the access_token is not there, the user might not able to post. check the permission
if ([result valueForKey:#"access_token"] != nil) {
NSString *accessToken = [result objectForKey:#"access_token"];
}
}];
After getting the Page's access_token, you need to post the image using REST API. Here I am using AFNetworking, and manually upload the image.
if ([result valueForKey:#"access_token"] != nil) {
NSString *accessToken = [result objectForKey:#"access_token"];
NSURL *url = [NSURL URLWithString:#"https://graph.facebook.com"];
AFHTTPClient *client = [AFHTTPClient clientWithBaseURL:url];
// parameter
NSDictionary *params = #{#"access_token": accessToken, #"message": message};
// image data
NSData *imageData = UIImageJPEGRepresentation(self.imagePreview.image, 1);
// create Request and upload the image
NSMutableURLRequest *request = [client multipartFormRequestWithMethod:#"POST" path:[NSString stringWithFormat:#"/%#/photos/", [defaults stringForKey:#"fb_page_id"]] parameters:params constructingBodyWithBlock:^(id<AFMultipartFormData> formData) {
[formData appendPartWithFileData:imageData name:#"source" fileName:accessToken mimeType:#"image/jpeg"];
}];
// publish!
AFJSONRequestOperation *json = [AFJSONRequestOperation JSONRequestOperationWithRequest:request1 success:^(NSURLRequest *request, NSHTTPURLResponse *response, id JSON) {
// IMAGE PUBLISHED!!!
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error, id JSON) {
// SOMETHING WRONG HAPPEN
}];
[json start];
}
Don't ask me why I'm using REST API, I tried everything using their SDK, but its always failed.
I hope somebody will find it usefull for this piece of codes.
Related
I don't want to use graph story. But all other methods are rejected by Facebook team with message: Please make sure you are not pre-filling message field.
for example:
NSMutableDictionary *params = [NSMutableDictionary dictionary];
[params setObject:text forKey:#"message"];
[params setObject:#"link" forKey:#"type"];
//[params setObject:#"http://google.com/" forKey:#"link"];
if(photoID) {
[params setObject:photoID forKey:#"object_attachment"];
}
FBRequestConnection *connection = [[FBRequestConnection alloc] init];
NSMutableDictionary* photosParams = [NSMutableDictionary dictionaryWithObjectsAndKeys:
image,#"source",
text,#"message",
nil];
FBRequest *request = [[FBRequest alloc] initWithSession:[FBSession activeSession]
graphPath:#"me/photos"
parameters:photosParams
HTTPMethod:#"POST"];
[connection addRequest:request completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
completionBlock(error);
}];
FBRequest *req = [FBRequest requestForGraphPath:#"me/feed"];
req.graphObject = (id<FBGraphObject>)[NSDictionary dictionaryWithDictionary:params];
[connection addRequest:req
completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
if (!error && result) {
NSLog(#"%#",result);
}
}
];
Please explain what method I should use in this case?
In case if correct behavior is use stories then why other methods are not marked as deprecated?
Thanks.
I am getting "permissions error" message when try to publish to app_link_hosts edge. Please advise me what am I doing wrong? I have checked Facebook permissions. I do have publish_actions permission and I can publish to user's wall no problem but cannot publish to app_link_hosts... Trying to set up a back link from a share link to my iOS app.
NSString *fbAccessToken = [[[FBSession activeSession] accessTokenData] accessToken];
NSString *theUrl = [NSString stringWithFormat:#"myscheme://deeplink?playlist_id=%#",[postParams objectForKey:#"playlist_id"]];
NSDictionary *params = [NSDictionary dictionaryWithObjectsAndKeys:
#"MY APP NAME", #"name",
theUrl, #"al:iphone:url",
#"77948767", #"al:iphone:app_store_id",
#"MY APP NAME", #"al:iphone:app_name",
#"{\"should_fallback\": false}", #"web",
fbAccessToken, #"access_token",
nil
];
/* make the API call */
[FBRequestConnection startWithGraphPath:#"/233246787764/app_link_hosts"
parameters:params
HTTPMethod:#"POST"
completionHandler:^(
FBRequestConnection *connection,
id result,
NSError *error
) {
/* handle the result */
NSLog(#"Result = %#",result);
if(error) NSLog(#"error = %#",error);
}];
I am trying to upload a video from my iPhone to Facebook. I have logged in using FBLoginView and created a FBSession. I have used the following code to initiate a FBRequest of upload the video.
- (void)buttonRequestClickHandler:(id)sender {
if (FBSession.activeSession.isOpen) {
[FBSession.activeSession requestNewPublishPermissions:permissions
defaultAudience:FBSessionDefaultAudienceOnlyMe
completionHandler:nil];
NSString *audioName = [pictureDictionary4 objectForKey:#"photoVideokey"];
NSArray *pathsa = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectorya = [pathsa objectAtIndex:0];
NSString *moviePath = [documentsDirectorya stringByAppendingPathComponent:#"/Movie"];
NSString *fullPatha = [moviePath stringByAppendingPathComponent:audioName];
NSURL *pathURL = [[NSURL alloc]initFileURLWithPath:fullPatha isDirectory:NO];
NSData *videoData = [NSData dataWithContentsOfFile:fullPatha];
NSString *titleString = self.videotitle.text;
NSString *descripString = self.descrp.text;
NSDictionary *videoObject = #{
#"title":titleString,
#"description": descripString,
[pathURL absoluteString]: videoData
};
FBRequest *uploadRequest = [FBRequest requestWithGraphPath:#"me/videos"
parameters:videoObject
HTTPMethod:#"POST"];
[uploadRequest startWithCompletionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
if (!error)
NSLog(#"Done: %#", result);
else
NSLog(#"Error: %#", error.localizedDescription);
}];
}
I get an error
Error: The operation couldn’t be completed. (com.facebook.sdk error 5.)
I'm not sure what the error pertains to:
I know I'm logged in
I don't know if I am getting connected but I am on internet with iPhone
Are my parameters incorrect?
I have been messing with this for HOURS with no results
Any help from anyone/everyone would be greatly appreciated.
Finally got this working by going into my iPhone settings-facebook and deleting my account. Then when I tapped to upload the video in my app it loaded a view that asked if Facebook could use my app and I said yes then bam it uploaded. Also had to change my permissions to just publish_actions and get rid of publish_streams since that is a read permission. Anyway it is working now. Next to get defaultAudience to load from a string picked by user and not hard coded. Another post.
I guess its something to do with stream publishing permission. Try this way. It worked for me. I was using Facebook SDK 3.8.0
[self performPublishAction:^{
NSString *filePath = [[NSBundle mainBundle] pathForResource:#"faisal" ofType:#"mov"];
NSURL *pathURL = [[NSURL alloc]initFileURLWithPath:filePath isDirectory:NO];
NSData *videoData = [NSData dataWithContentsOfFile:filePath];
NSDictionary *videoObject = #{
#"title": #"This is my title",
#"description": #"This is my description",
[pathURL absoluteString]: videoData
};
FBRequest *uploadRequest = [FBRequest requestWithGraphPath:#"me/videos"
parameters:videoObject
HTTPMethod:#"POST"];
[uploadRequest startWithCompletionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
if (!error)
NSLog(#"Done: %#", result);
else
NSLog(#"Error: %#", error.localizedDescription);
}];
}];
and
- (void) performPublishAction:(void (^)(void)) action {
if ([FBSession.activeSession.permissions indexOfObject:#"publish_stream"] == NSNotFound) {
[FBSession.activeSession requestNewPublishPermissions:#[#"publish_stream"]
defaultAudience:FBSessionDefaultAudienceFriends
completionHandler:^(FBSession *session, NSError *error) {
if (!error) {
action();
} else if (error.fberrorCategory != FBErrorCategoryUserCancelled){
UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:#"Permission denied"
message:#"Unable to get permission to post"
delegate:nil
cancelButtonTitle:#"OK"
otherButtonTitles:nil];
[alertView show];
}
}];
} else {
action();
}
}
This Code is Tested successfully On FaceBook SDK 3.14.1
Recommendation: 3 properties in .plist file
set FacebookAppID,FacebookDisplayName,
URL types->Item 0->URL Schemes set to facebookappId prefix with fb See
-(void)shareOnFaceBook
{
//sample_video.mov is the name of file
NSString *filePathOfVideo = [[NSBundle mainBundle] pathForResource:#"sample_video" ofType:#"mov"];
NSLog(#"Path Of Video is %#", filePathOfVideo);
NSData *videoData = [NSData dataWithContentsOfFile:filePathOfVideo];
//you can use dataWithContentsOfURL if you have a Url of video file
//NSData *videoData = [NSData dataWithContentsOfURL:shareURL];
//NSLog(#"data is :%#",videoData);
NSMutableDictionary *params = [NSMutableDictionary dictionaryWithObjectsAndKeys:
videoData, #"video.mov",
#"video/quicktime", #"contentType",
#"Video name ", #"name",
#"description of Video", #"description",
nil];
if (FBSession.activeSession.isOpen)
{
[FBRequestConnection startWithGraphPath:#"me/videos"
parameters:params
HTTPMethod:#"POST"
completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
if(!error)
{
NSLog(#"RESULT: %#", result);
[self throwAlertWithTitle:#"Success" message:#"Video uploaded"];
}
else
{
NSLog(#"ERROR: %#", error.localizedDescription);
[self throwAlertWithTitle:#"Denied" message:#"Try Again"];
}
}];
}
else
{
NSArray *permissions = [[NSArray alloc] initWithObjects:
#"publish_actions",
nil];
// OPEN Session!
[FBSession openActiveSessionWithPublishPermissions:permissions defaultAudience:FBSessionDefaultAudienceEveryone allowLoginUI:YES
completionHandler:^(FBSession *session,
FBSessionState status,
NSError *error) {
if (error)
{
NSLog(#"Login fail :%#",error);
}
else if (FB_ISSESSIONOPENWITHSTATE(status))
{
[FBRequestConnection startWithGraphPath:#"me/videos"
parameters:params
HTTPMethod:#"POST"
completionHandler:^(FBRequestConnection *connection, id result, NSError *error) {
if(!error)
{
[self throwAlertWithTitle:#"Success" message:#"Video uploaded"];
NSLog(#"RESULT: %#", result);
}
else
{
[self throwAlertWithTitle:#"Denied" message:#"Try Again"];
NSLog(#"ERROR: %#", error.localizedDescription);
}
}];
}
}];
}
}
And I GOT Error:
The operation couldn’t be completed. (com.facebook.sdk error 5.)
It happens when facebook is being inited. Next time i open my app, it works fine, its always the first time. Tried everything in app, but it seems to be on the Facebook SDK side.
Few causes for seeing com.facebook.sdk error 5:
Session is is not open. Validate.
Facebook has detected that you're spamming the system. Change video name.
Facebook has a defined limit using the SDK. Try a different app.
Wrong publish permission. Give publish_actions a spin.
In my application I'm getting friend list of logged in user and by selecting any one I can get his details like name, photo, id etc.
But my question is that I need to send message to selected user by using his details like id with Facebook SDK 3.1.
if you want to post to users wall try this one :
NSMutableDictionary *postTest = [[NSMutableDictionary alloc]init];
[postTest setObject:[NSString stringWithFormat#"Your message"] forKey:#"message"];
[postTest setObject:#"" forKey:#"picture"];
[postTest setObject:#"" forKey:#"name"];
[postTest setObject:#"APPID" forKey:#"app_id"];
NSString *userFBID =[NSString stringWithFormat:#"%#",[allInfoDict objectForKey:#"Friends facebook ID "]];
[FBRequestConnection startWithGraphPath:[NSString stringWithFormat:#"%#/feed?access_token=%#",userFBID,[appDelegate.mysession accessToken]]
parameters:postTest
HTTPMethod:#"POST"
completionHandler:^(FBRequestConnection *connection,
NSDictionary * result,
NSError *error) {
if (error) {
[self hideHUD];
NSLog(#"Error: %#", [error localizedDescription]);
} else {
// Success
}
}];
[postTest release];
I am trying to query information about a user using iOS 6's new Facebook integration API. This is the code I'm using, which is basically identical to what they demoed at WWDC:
{
NSDictionary *parameters = #{};
NSURL *url = [NSURL URLWithString:#"https://graph.facebook.com/me"];
SLRequest *request = [SLRequest requestForServiceType:SLServiceTypeFacebook
requestMethod:SLRequestMethodGET
URL:url
parameters:parameters];
request.account = self.account;
[request performRequestWithHandler:^(NSData *responseData, NSHTTPURLResponse *urlResponse, NSError *error) {
NSLog(#"Facebook request received, status code %d", urlResponse.statusCode);
NSString *response = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding];
NSLog(#"Response data: %#", response);
dispatch_async(dispatch_get_main_queue(), ^{
});
}];
}
Problem is I am getting error code 2500 from Facebook: "An active access token must be used to query information about the current user." If I change the query to https://graph.facebook.com/[facebook id] then it works fine. I am assuming the problem is that iOS is passing the access token of the app instead of the user's access token when sending the request via requestForServiceType. I just don't know how to fix it. Obviously anticipating and hardcoding the Facebook IDs of my users is not an option. Any suggestions?
add your active access token in paramete like
NSDictionary *parameters = [NSDictionary dictionaryWithObject:#"PUT_ACCESS_TOKEN_HERE" forKey:#"access_token"];
I faced with the same issue and found the workaround:
NSString *uid = [NSString stringWithFormat:#"%#", [[self.account valueForKey:#"properties"] valueForKey:#"uid"]] ;
NSURL *url = [NSURL URLWithString:[#"https://graph.facebook.com" stringByAppendingPathComponent:uid]];
OK here is how I do this integration with iOS 6 and get what I want from Facebook:
In AppDelegate I do this:
- (BOOL)application:(UIApplication *)application
openURL:(NSURL *)url
sourceApplication:(NSString *)sourceApplication
annotation:(id)annotation {
return [FBSession.activeSession handleOpenURL:url];
}
- (void)applicationDidBecomeActive:(UIApplication *)application
{
[FBSession.activeSession handleDidBecomeActive];
}
- (void)applicationWillTerminate:(UIApplication *)application
{
[FBSession.activeSession close];
}
and in my ViewController where I want to retrieve information about myself or my friends I do this (NOTE: this is a test, so it is a lot of permissions!):
NSArray *permissions =
[NSArray arrayWithObjects:#"email", #"user_location",
#"user_birthday",
#"user_likes", #"user_interests",#"friends_interests",#"friends_birthday",#"friends_location",#"friends_hometown",#"friends_photos",#"friends_status",
#"friends_about_me", #"friends_birthday", #"friends_hometown", #"friends_interests", #"friends_likes", #"friends_location", nil];
[FBSession openActiveSessionWithReadPermissions:permissions
allowLoginUI:YES
completionHandler:^(FBSession *session, FBSessionState status, NSError *error) {
/* handle success + failure in block */
if (status) {
NSLog(#"Facebook Read Permission is successful!");
[self presentPostOptions];
// [self presentPostOptions];
}
}];
Then in "presentPostOptions" I do this (in this example I try to retrieve something from my friend):
- (void)presentPostOptions
{
[[FBRequest requestForMyFriends] startWithCompletionHandler:^(FBRequestConnection *connection, NSDictionary<FBGraphUser> *user, NSError *error)
{
if (!error) {
NSArray *data = [user objectForKey:#"data"];
NSLog(#"%d", [data count]);
for (FBGraphObject<FBGraphUser> *friend in data) {
NSLog(#"%#", [friend first_name]);
NSLog(#"%#", [friend last_name]);
NSLog(#"%#", [friend id]);
//make sure you have FBProfilePictureView outlet in your view
//otherwise skip the profile picture!
self.fbProfilePic.profileID = #"you'r friend's profile.id";
}
}
else
{
NSLog(#"error");
// [self didFailWithError:error];
}
}];
I don't know what else you want to do because in your question you just tried to make a connection but this way you can do what ever you want while you are integrated in iOS 6.
One more thing, make sure about your App Settings over Facebook and the configs over there like enable your app for iOS and the ID for iPhone/iPad. Also the FacebookAppID in your plist.
Let me know if it works out for you,
EDIT: btw my Facebook SDK is 3.1.1.
I had the same error message, I fixed it by saving my account after renewing the credential.
Make sure your (ACAccount *)facebookAccount (or in your case self.account)
object is strong and you set it correctly while getting permissions.
The answer is simple
in viewDidLoad() use:
accountStore= [[ACAccountStore alloc]init];
facebookAccountType= [accountStore accountTypeWithAccountTypeIdentifier:ACAccountTypeIdentifierFacebook];
NSDictionary *options= #{
ACFacebookAudienceKey: ACFacebookAudienceEveryone,
ACFacebookAppIdKey: #"<YOUR FACEBOOK APP ID>",
ACFacebookPermissionsKey: #[#"public_profile"]
};
[accountStore requestAccessToAccountsWithType:facebookAccountType options:options completion:^(BOOL granted, NSError *error) {
if (granted) {
NSLog(#"Permission has been granted to the app");
NSArray *accounts= [accountStore accountsWithAccountType:facebookAccountType];
facebookAccount= [accounts firstObject];
[self performSelectorOnMainThread:#selector(facebookProfile) withObject:nil waitUntilDone:NO];
} else {
NSLog(#"Permission denied to the app");
}
}];
And the function-(void)facebookProfile
NSURL *url = [NSURL URLWithString:#"https://graph.facebook.com/me"];
Notice the params you need are added as dictionary
Refer below for complete list
https://developers.facebook.com/docs/graph-api/reference/user
NSDictionary *param=[NSDictionary dictionaryWithObjectsAndKeys:#"picture,id,name",#"fields", nil];
SLRequest *profileInfoRequest= [SLRequest requestForServiceType:SLServiceTypeFacebook requestMethod:SLRequestMethodGET URL:url parameters:param];
profileInfoRequest.account= facebookAccount;
[profileInfoRequest performRequestWithHandler:^(NSData *responseData, NSHTTPURLResponse *urlResponse, NSError *error) {
NSLog(#"Facebook status code is : %ld", (long)[urlResponse statusCode]);
if ([urlResponse statusCode]==200) {
NSDictionary *dictionaryData= [NSJSONSerialization JSONObjectWithData:responseData options:NSJSONReadingMutableLeaves error:&error];
} else {
}
}];
}