I am using facebook graph request to retrieve friends list. But, How can I get to create a function and return it after the call graphRequest.executeAsync()
is done?.
private Map<String, String> getFacebookFriends(AccessToken accessToken, Profile profile) throws InterruptedException, ExecutionException {
final Map<String, String> friendsMap = new HashMap<>();
GraphRequest graphRequest = new GraphRequest(accessToken, "/me/friends", null, HttpMethod.GET,
new GraphRequest.Callback() {
public void onCompleted(GraphResponse response) {
JSONObject jGraphObj = response.getJSONObject();
try {
JSONArray friendsData = jGraphObj.getJSONArray("data");
for (int i = 0; i < friendsData.length(); i++) {
JSONObject friend = friendsData.getJSONObject(i);
String friendId = friend.getString("id");
String friendName = friend.getString("name");
friendsMap.put(friendId, friendName);
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
);
List<GraphResponse> gResponseList = graphRequest.executeAsync().get();
return friendsMap;
}
I am currently using the same technique like in this post. By calling it like graphRequest.executeAsync().get();
. But it seems like it's not working.
The function above will return the friendsMap
before the graphRequest
is done.
Any suggestion is appreciated.
I've got this working by using executeAndWait
instead of executeAsync
function. So, this is how the final looks like
public static Map<String, String> getFacebookFriends(AccessToken accessToken, Profile profile) throws InterruptedException, ExecutionException {
final Map<String, String> friendsMap = new HashMap<>();
GraphRequest.Callback gCallback = new GraphRequest.Callback() {
public void onCompleted(GraphResponse response) {
JSONObject jGraphObj = response.getJSONObject();
try {
JSONArray friendsData = jGraphObj.getJSONArray("data");
for (int i = 0; i < friendsData.length(); i++) {
JSONObject friend = friendsData.getJSONObject(i);
String friendId = friend.getString("id");
String friendName = friend.getString("name");
friendsMap.put(friendId, friendName);
}
} catch (Exception e) {
e.printStackTrace();
}
}
};
final GraphRequest graphRequest = new GraphRequest(accessToken, "/me/friends", null, HttpMethod.GET, gCallback);
// Run facebook graphRequest.
Thread t = new Thread(new Runnable() {
@Override
public void run() {
GraphResponse gResponse = graphRequest.executeAndWait();
}
});
t.start();
t.join();
return friendsMap;
}
For anyone who needs the version in C#. This is what I have in my Main activity.
public static ICallbackManager CallbackManager = CallbackManagerFactory.Create();
protected override void OnCreate(Bundle bundle)
{
base.OnCreate(bundle);
var facebookCallback = new FacebookCallback<LoginResult>
{
HandleSuccess = async shareResult =>
{
Bundle parameters = new Bundle();
parameters.PutString("fields", "id,name,link,email,picture.type(normal),friends");
GraphRequest request = new GraphRequest(
shareResult.AccessToken,
"/me",
parameters, HttpMethod.Get, new OnGraphResulCallback());
await Task.Run(() =>
{
var fbResponse = JsonConvert.DeserializeObject<FbResponse>(request.ExecuteAndWait().RawResponse);
});
},
HandleCancel = () =>
{
Console.WriteLine("HelloFacebook: Canceled");
},
HandleError = shareError =>
{
Console.WriteLine("HelloFacebook: Error: {0}", shareError);
}
};
// fb init
FacebookSdk.SdkInitialize(this.ApplicationContext);
LoginManager.Instance.RegisterCallback(MainActivity.CallbackManager, facebookCallback);
Forms.Init(this, bundle);
LoadApplication(App.Instance);
}
and here are the helper classes:
public class FacebookCallback<TResult> : Java.Lang.Object, IFacebookCallback where TResult : Java.Lang.Object
{
public Action HandleCancel { get; set; }
public Action<FacebookException> HandleError { get; set; }
public Action<TResult> HandleSuccess { get; set; }
public void OnCancel()
{
HandleCancel.Invoke();
}
public void OnError(FacebookException error)
{
HandleError.Invoke(error);
}
public void OnSuccess(Java.Lang.Object result)
{
HandleSuccess.Invoke(result.JavaCast<TResult>());
}
}
public class FbResponse
{
public long Id { get; set; }
public string Name { get; set; }
public Picture Picture { get; set; }
public Friends Friends { get; set; }
public string Email { get; set; }
}
public class Friends
{
public List<FriendsData> Data { get; set; }
public Paging Paging { get; set; }
public Summary Summary { get; set; }
}
public class Summary
{
public int Total_Count { get; set; }
}
public class Paging
{
public Cursors Cursors { get; set; }
}
public class Cursors
{
public string Before { get; set; }
public string After { get; set; }
}
public class FriendsData
{
public int Id { get; set; }
public string Name { get; set; }
}
public class Picture
{
public PictureData Data { get; set; }
}
public class PictureData
{
public bool Is_Silhouette { get; set; }
public string Url { get; set; }
}