我在这个主题上找不到任何帮助。文件说
基于游标的分页是最有效的分页方法,应尽可能使用 - 游标是指随机字符串,用于标记数据列表中的特定项目。除非删除此项,否则光标将始终指向列表的相同部分,但如果删除项,则无效。因此,您的应用不应存储任何旧游标或假设它们仍然有效。
When reading an edge that supports cursor pagination, you will see the following JSON response:
{
"data": [
... Endpoint data is here
],
"paging": {
"cursors": {
"after": "MTAxNTExOTQ1MjAwNzI5NDE=",
"before": "NDMyNzQyODI3OTQw"
},
"previous": "https://graph.facebook.com/me/albums?limit=25&before=NDMyNzQyODI3OTQw"
"next": "https://graph.facebook.com/me/albums?limit=25&after=MTAxNTExOTQ1MjAwNzI5NDE="
}
}
我使用这种格式进行api调用,如何遍历循环中的所有页面
/* make the API call */
new GraphRequest(
session,
"/{user-id}/statuses",
null,
HttpMethod.GET,
new GraphRequest.Callback() {
public void onCompleted(GraphResponse response) {
/* handle the result */
}
}
).executeAsync();
答案 0 :(得分:12)
我想出了一个使用光标分页遍历facebook图表api页面的好方法
final String[] afterString = {""}; // will contain the next page cursor
final Boolean[] noData = {false}; // stop when there is no after cursor
do {
Bundle params = new Bundle();
params.putString("after", afterString[0]);
new GraphRequest(
accessToken,
personId + "/likes",
params,
HttpMethod.GET,
new GraphRequest.Callback() {
@Override
public void onCompleted(GraphResponse graphResponse) {
JSONObject jsonObject = graphResponse.getJSONObject();
try {
JSONArray jsonArray = jsonObject.getJSONArray("data");
// your code
if(!jsonObject.isNull("paging")) {
JSONObject paging = jsonObject.getJSONObject("paging");
JSONObject cursors = paging.getJSONObject("cursors");
if (!cursors.isNull("after"))
afterString[0] = cursors.getString("after");
else
noData[0] = true;
}
else
noData[0] = true;
} catch (JSONException e) {
e.printStackTrace();
}
}
}
).executeAndWait();
}
while(!noData[0] == true);
答案 1 :(得分:10)
不要重新发明轮子。
GraphResponse类已经有了一种方便的分页方法。 GraphResponse.getRequestForPagedResults()
返回 GraphRequest
个对象,您可以使用该对象进行分页。
我还找到了来自facebook-android-sdk's unit test code的代码段。
GraphRequest nextRequest = response.getRequestForPagedResults(GraphResponse.PagingDirection.NEXT);
nextRequest.setCallback(request.getCallback());
response = nextRequest.executeAndWait();
答案 2 :(得分:5)
虽然您应该使用GraphResponse.getRequestForPagedResults()
,但除非您在其他主题中运行,否则无法使用executeAndWait()
。
使用executeAsync()
可以更轻松。
获取第一组结果:
new GraphRequest(AccessToken.getCurrentAccessToken(),
"/" + facebookID + "/invitable_friends",
null,
HttpMethod.GET,
new GraphRequest.Callback() {
public void onCompleted(GraphResponse response) {
//your code
//save the last GraphResponse you received
lastGraphResponse = response;
}
}
).executeAsync();
使用lastGraphResponse 获取下一组结果:
GraphRequest nextResultsRequests = lastGraphResponse.getRequestForPagedResults(GraphResponse.PagingDirection.NEXT);
if (nextResultsRequests != null) {
nextResultsRequests.setCallback(new GraphRequest.Callback() {
@Override
public void onCompleted(GraphResponse response) {
//your code
//save the last GraphResponse you received
lastGraphResponse = response;
}
});
nextResultsRequests.executeAsync();
}
您可以在一个方法中合并所有内容!
答案 3 :(得分:3)
我使用此代码:
final String[] afterString = {""};
final Boolean[] noData = {true};
StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();
StrictMode.setThreadPolicy(policy);
do{
GraphRequest request = GraphRequest.newGraphPathRequest(
AccessToken.getCurrentAccessToken(),
"/me/likes",
new GraphRequest.Callback() {
@Override
public void onCompleted(GraphResponse response) {
// Insert your code here
JSONObject jsonObject = response.getJSONObject();
try{
if(jsonObject.length() > 1) {
JSONObject jsonFacebook = (JSONObject) new JSONTokener(jsonObject.toString()).nextValue();
JSONObject likes_paging = (JSONObject) new JSONTokener(jsonFacebook.getJSONObject("paging").toString()).nextValue();
ArrayList<String> likes = new ArrayList<String>();
for (int i = 0; i < jsonFacebook.getJSONArray("data").length(); i++) {
likes.add(jsonFacebook.getJSONArray("data").getJSONObject(i).getString("name"));
}
afterString[0] = (String) likes_paging.getJSONObject("cursors").get("after");
}else{
noData[0] = false;
}
} catch (JSONException e) {
e.printStackTrace();
}
}
});
Bundle parameters = new Bundle();
parameters.putString("pretty", "0");
parameters.putString("limit", "100");
parameters.putString("after", afterString[0]);
request.setParameters(parameters);
request.executeAndWait();
}while(noData[0] == true);
答案 4 :(得分:0)
我在项目中所做的基本上是在onSearchClicked()
中进行首次调用,并在ViewModel的onCompleted()
回调中获得结果。如果nextRequest
为空,我将结果列表返回到片段,否则返回下一个调用,直到到达末尾(nextRequest == null
)。然后,将累积的列表返回到片段。
class SearchViewModel() : GraphRequest.Callback {
private var allPlaces = arrayListOf<FacebookPlace>()
fun onSearchClicked(location: Location) {
val request = GraphRequest.newGraphPathRequest(accessToken, "/search", this)
request.parameters = parameters
request.executeAsync()
}
override fun onCompleted(response: GraphResponse?) {
if (response != null) {
allPlaces.addAll(response.data)
val nextRequest = response.getRequestForPagedResults(GraphResponse.PagingDirection.NEXT)
if (nextRequest == null) {
uiEvent.value = ShowPlaces(allPlaces)
} else {
nextRequest.callback = this
nextRequest.executeAsync()
}
} else {
Log.e(TAG, "Search response is null.")
}
}