Basically, I have a custom object inheriting from place. I am creating a c# tool for creating the objects using the Facebook Sharp c# SDK located here I am using an app access token when making these calls.
I've tried various approaches and variation within:
Here is a sample call that yeilds:
(OAuthException - #100) (#100) The parameter object is required
_api.AccessToken = GetExtendedToken().Token;
var postdata = new Dictionary<string, object>
{
//{"fb:app_id", "appId"},
//{"type", "myapp:myobject"},
{"url", resort.Url},
{"title", resort.Name },
{"image", resort.Image},
{"video", resort.Video},
{"description", resort.Description},
{"place:location:latitude", lat},
{"place:location:longitude", long}
};
var response = _api.Post("/app/objects/myapp:myobject", postdata);
if I uncomment the type parameter I get:
(OAuthException - #2500) Cannot specify type in both the path and query parameter
If I add the type back in, and remove the type from the path, I get
a response of true but this should be something like id:
23049820398092384
If I remove the place objects, or if I remove place and type, or if
I remove place but use the type and change the get path, I still get
errors.
refactored a bit. In this scenario I needed to assign the postdata information to an object as such below. also needed to stop using facebooksharp, their api does weird stuff to the request.
var obj = new
{
app_id = appId,
type = app_name:object_type",
url = Url,
title = Name,
image = Image,
video = Video,
description = Description
};
var vars = new NameValueCollection {{"object", JsonConvert.SerializeObject(obj)}, {"format", "json"}, {"access_token", AppToken}};
var url = "https://graph.facebook.com/app/objects/"+ _appName + object_type;
return HttpTools.Post(url, vars);
Related
Is it possible to append a segment to a MS Graph GraphServiceClient Request and fetch that resource?
The scenario:
I want to get the root site of a group (more specifically its weburl property)
https://graph.microsoft.com/v1.0/groups/{group-id}/sites/root
but it is not possible to append the /root segment with the QueryBuilder and enumerating sites is not allowed and throws an exception
var task = graphClient.Groups[group.Id].Sites.Request().GetAsync() // exception
I can get the string for the request
var url = graphClient.Groups[group.Id].Sites.Request().AppendSegmentToRequestUrl("root")
But then I would need a method to which I can supply a full Graph Url, for example:
graphClient.MakeRequest(url).GetAsync()
I know I could use the HttpClient Class but that would introduce a different pattern to fetch Graph Resources and I would like to avoid that.
Edit - Solution
Seems as if you have to play with the RequestBuilders that are available under the Microsoft.Graph namespace until you find one that matches the type of your request, all the others return null.
var requestBuilder = client.Groups["guid-of-group"].Sites;
var url = requestBuilder.AppendSegmentToRequestUrl("root");
GroupRequestBuilder builder = new GroupRequestBuilder(url, client);
var result = await builder.Request().GetAsync();
Perharps you could try something like this and pass in the graphServiceClient and created url to a new instance of a request builder.
// create the url from the builders
var requestBuilder = graphClient.Groups["groupId"].Sites;
var url = request.AppendSegmentToRequestUrl("root");
// we have to create a new builder as the url property cannot be set/modified publicly
GroupSitesCollectionRequestBuilder groupSitesCollectionRequestBuilder = new GroupSitesCollectionRequestBuilder(url, graphClient);
// Make the call
var result = await groupSitesCollectionRequestBuilder.Request().GetAsync();
I'm trying to copy and move objects between buckets in Google Cloud Storage using the .NET API. As far as I can tell I am constructing the request correctly and I have verified that all the properties I am setting below are correct and what they should be but I get the following cryptic error:
Google.GoogleApiException : Google.Apis.Requests.RequestError
Required [400]
Errors [
Message[Required] Location[ - ] Reason[required] Domain[global]
]
here is the code
Google.Apis.Storage.v1.Data.Object moveObj = new Google.Apis.Storage.v1.Data.Object() { Name = key, Size = (ulong)Length, ContentType = contentType };
ObjectsResource.RewriteRequest req = new ObjectsResource.RewriteRequest(_gcsClient, newObj,sourceBucket, key, destBucket, key);
req.Execute();
Any idea what I might be doing wrong?
I figured it out on my own, hopefully this answer will help you if you're having the same issue. Credit this the poorly written and inconsistent Cloud Storage API more than anything. Every other operation when you create a Storage 'Object' you specify the name for it (see first param):
new Google.Apis.Storage.v1.Data.Object() { Name = key, Size = (ulong)Length, ContentType = contentType };
But for some reason this breaks when trying to move or copy the object so in this case you can omit it as you are passing the destinationKey as a property to the WriteRequest/CopyRequest anyway, so like this:
new Google.Apis.Storage.v1.Data.Object() {Size = (ulong)Length, ContentType = contentType };
Here is my generate URL:
private Uri GenerateLoginUrl(string appId, string extendedPermissions)
{
// for .net 3.5
// var parameters = new Dictionary<string,object>
// parameters["client_id"] = appId;
dynamic parameters = new ExpandoObject();
parameters.client_id = appId;
parameters.redirect_uri = "https://www.facebook.com/connect/login_success.html";
// The requested response: an access token (token), an authorization code (code), or both (code token).
parameters.response_type = "token";
// list of additional display modes can be found at http://developers.facebook.com/docs/reference/dialogs/#display
parameters.display = "popup";
//scope
parameters.scope = "Email";
// add the 'scope' parameter only if we have extendedPermissions.
if (!string.IsNullOrWhiteSpace(extendedPermissions))
parameters.scope = extendedPermissions;
// when the Form is loaded navigate to the login url.
return _fb.GetLoginUrl(parameters);
//webBrowser.Navigate(new Uri("www.facebook.com"));
}
The problem is the return _fb.GetLoginUrl is NULL. I have a webBrowser control already on the WinForm.
Any ideas? or can i just hard code the URL?
Worked at this a few months ago. I had the same problem cause by the ajax in the response site. The problem is that the ajax load the site content after the url is loaded. I fixed it by wait for the webbrowseres load event. I think it was webrowser.DocumentCompleted
I hope this help you.
I have used JSDK to authenticate user for my facebook app.
I am getting the access token but it gets expired within 1/2 hours.
So how can I get long term Access Token?
The code I have used is:
var fb = new FacebookClient();
Dictionary<string,Object> sParams=new Dictionary<string,Object>();
sParams.Add("client_id",My_App_ID);
sParams.Add("client_secret",My_App_Secret);
sParams.Add("grant_type","fb_exchange_token");
sParams.Add("fb_exchange_token",Short_lived_accessToken);
dynamic result = fb.Get("oauth/access_token",sParams);
fb.AccessToken = result.access_token;
but it gives me error Invalid JSON String at line dynamic result = fb.Get("oauth/access_token",sParams);
What wrong am I doing here?
Use this code:
var client = new FacebookClient(Short_lived_accessToken);
dynamic result = client.Post("oauth/access_token", new
{
client_id = My_App_ID,
client_secret = My_App_Secret,
grant_type = "fb_exchange_token",
fb_exchange_token = Short_lived_accessToken
});
Response.Write("Long live access token: [" + result.access_token + "]");
Hope it helps.
The return you will get from the endpoint simply is not JSON, but just plain text in the form
access_token=new_long-lived_access_token&expires=5130106
So you will have to tell your application somehow(?), that the result is not JSON; or you might have to use a different method altogether to make the request, if FacebookClient::Get always expects the answer to be JSON.
I'm trying to upload a video to the Facebook open graph using the C# SDK. The video seems to upload fine and I get an Id for the activity, but only the sample metadata appears.
After a little digging, I found this:
Before being able to publish an Open Graph action for a user and having define its corresponding connected object type in Step 3, you will now need to create a publicly accessible web page that represents this object using Open Graph metatags. Once this object page is created, you can use the Graph API to publish an action.
Since this is a client-side app, I don't have a web page that I can refer Facebook to. So how do I pass in the right parameters?
Here's my code:
var parameters = new Dictionary<string, object>();
parameters["source"] = new FacebookMediaObject { ContentType = "video/mpeg", FileName = "video.mpeg" }.SetValue(File.ReadAllBytes(#"D:\sample video.MP4"));
parameters["og:title"] = "Sample video";
parameters["title"] = "Sample video";
parameters["og:description"] = "Test description";
parameters["highlight"] = "http://samples.ogp.me/287287444686523"; // If I don't put this, the upload fails
fb.PostAsync("/me/myobjectname:share", parameters);
Thanks!
For version 6, you can do:
var fb = new FacebookClient(accessToken);
string attachementPath = #"C:\image.jpg";
using (var stream = File.OpenRead(attachementPath))
{
dynamic result = fb.Post("me/photos",
new
{
message = "upload using Facebook C# SDK",
file = new FacebookMediaStream
{
ContentType = "image/jpg",
FileName = Path.GetFileName(attachementPath)
}.SetValue(stream)
});
}
More details here.