I have implemented a function using Graph SDK based on the public documentation found here:
https://learn.microsoft.com/en-us/graph/paging
While it is working, the callback is called correctly by each 2 items (Top(2)), the subsequent iterations (@odata.nextLink) contain overlapping person objects.
If I use a higher number in Top than the total number of people in the folder, e.g. Top(100), then all Persons are delivered correctly.
My first thought was that it may failed because because of a missing order by clause, but it still keeps failing after adding it.
Comment by user2250152 on SO:
Looks like a bug in Graph API. I've tried your query
(graph.microsoft.com/v1.0/users{user_id}/people?$top=2&$select=displayName,scoredEmailAddresses&$orderBy=displayName)
in Graph Explorer (developer.microsoft.com/en-us/graph/graph-explorer) and the query returns still the same two records for each page.
My original SO question: (https://stackoverflow.com/questions/71811808/graph-pageiterator-returns-same-items-multiple-times)
public async Task<Dictionary<string, string>> LoadDisplayNames(string UserId)
{
User GRAPHUser = await GetUser(UserId);
Dictionary<string, string> ret = new Dictionary<string, string>();
try
{
var Persons = await _service.Users[GRAPHUser.Id].People.Request()
.Top(2)
.OrderBy("displayName")
.Select(e => new
{
e.ScoredEmailAddresses,
e.DisplayName
})
.GetAsync();
var pageIterator = PageIterator<Person>.CreatePageIterator(
_service,
Persons,
(p) =>
{
var HighestScoreAddress = p.ScoredEmailAddresses.OrderBy(a => a.RelevanceScore).FirstOrDefault();
if (HighestScoreAddress != null && !ret.ContainsKey(HighestScoreAddress.Address))
{
var email = HighestScoreAddress.Address.Replace("SMTP:", "");
ret.Add(email, $"{p.DisplayName} ({email})");
}
return true;
}
);
await pageIterator.IterateAsync();
}
catch (Exception ex)
{
Logger.Error(ex, ex.Message);
}
return ret;
}