Pagination of API responses #601
Replies: 28 comments 54 replies
-
@yesoreyeram this looks pretty good and useful. Do you have any date in mind releasing this? Thanks! |
Beta Was this translation helpful? Give feedback.
-
The hard limit of 5 pages max is too low of a limit. Understand trying to protect the source however for large datasets more pages are required. |
Beta Was this translation helpful? Give feedback.
-
Hi , |
Beta Was this translation helpful? Give feedback.
-
I'm also facing the issue of the hard limit of 5 pages max is too low of a limit. The target API im using has a hard limit of 13 records (dont ask me why) and cant be changed by input. So in this case it will only pull 65 records what is to low because in my case there are more records to process. |
Beta Was this translation helpful? Give feedback.
-
Regarding the way of paging is working. I have some trouble te find out how to parse nested data when they are been paged. There seems is a differand behaver when the data is collected when using paging, and the inline option. So when the data is been loaded trough the api, and is paged, we have/see the data returned in the 5 rows. The nested data we want is that in "hits" from the api, there are 13 items in it. So now i will tell the plugin that the root is:
When i change it to: So i have striped down the json, create a array of 2 and use it as inline data: [{
"hits": [
{
"id": 1,
"provider": "x",
"description": "x",
"published": 1,
"properties": {
"A": true,
"B": true
},
"media": [
{
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
},
{
"id": "456",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
}
],
"location": {
"lat": "1.32",
"lon": "1.01"
},
"address": "x",
"agent": {
"id": 1,
"name": "x"
},
"city": "x",
"features": [],
"_id": "1",
"priceInfo": {
"price": "1.00"
},
"photo": {
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"type": 2,
"orientation": "landscape"
},
"link": "x"
},
{
"id": 2,
"provider": "x",
"description": "x",
"published": 1,
"properties": {
"A": true,
"B": true
},
"media": [
{
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
},
{
"id": "456",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
}
],
"location": {
"lat": "1.32",
"lon": "1.01"
},
"address": "x",
"agent": {
"id": 1,
"name": "x"
},
"city": "x",
"features": [],
"_id": "2",
"priceInfo": {
"price": "1.00"
},
"photo": {
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"type": 2,
"orientation": "landscape"
},
"link": "x"
}
],
"center": {
"lat": 1.87,
"lon": 1.45
},
"total": 87,
"pages": 7,
"page": 1,
"totalDisplay": 87,
"description": ""
},
{
"hits": [
{
"id": 3,
"provider": "x",
"description": "x",
"published": 1,
"properties": {
"A": true,
"B": true
},
"media": [
{
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
},
{
"id": "456",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
}
],
"location": {
"lat": "1.32",
"lon": "1.01"
},
"address": "x",
"agent": {
"id": 1,
"name": "x"
},
"city": "x",
"features": [],
"_id": "3",
"priceInfo": {
"price": "1.00"
},
"photo": {
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"type": 2,
"orientation": "landscape"
},
"link": "x"
},
{
"id": 4,
"provider": "x",
"description": "x",
"published": 1,
"properties": {
"A": true,
"B": true
},
"media": [
{
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
},
{
"id": "456",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"orientation": "landscape"
}
],
"location": {
"lat": "1.32",
"lon": "1.01"
},
"address": "x",
"agent": {
"id": 1,
"name": "x"
},
"city": "x",
"features": [],
"_id": "4",
"priceInfo": {
"price": "1.00"
},
"photo": {
"id": "123",
"formats": {
"xxs": "xxs.jpg",
"xs": "xs.jpg"
},
"type": 2,
"orientation": "landscape"
},
"link": "x"
}
],
"center": {
"lat": 1.87,
"lon": 1.45
},
"total": 87,
"pages": 7,
"page": 2,
"totalDisplay": 87,
"description": ""
}] Whenever i now apply the paring ps, after some hours debugging the json file , seems that there is a strange behaver of it and found that the items in {
"hits": [
{
"anumber": "",
"anumber_base": ""
},
{
"anumber": "121",
"anumber_base": 121
}
]
} |
Beta Was this translation helpful? Give feedback.
-
Beta Was this translation helpful? Give feedback.
-
Hello, your solution is great. |
Beta Was this translation helpful? Give feedback.
-
@yesoreyeram hello this is amazing stuff thank you for your work, i have a question thought. when using Iterating URLs in a loop is there a way to add the variable that i used to loop as a column to have that value in each row to know to which variable value it belongs to? |
Beta Was this translation helpful? Give feedback.
-
Hello, I solved pagination problem by adding multiple queries A,B,C for example. in A i used per_page=100 and number page_number 1 , for B per_page=100 and page_number 2. Then I merge using the transformation Merge by Id. I got all elements of page one and two in the same dashboard. This is without BACKEND parser, it works with UQL Thank you |
Beta Was this translation helpful? Give feedback.
-
Beta Was this translation helpful? Give feedback.
-
Correct me if I'm wrong, but I don't really understand the |
Beta Was this translation helpful? Give feedback.
-
This has been mentioned numerous times in this thread, but I also believe the '5 pages' limitation should be configurable. Even when examining Grafana's native APIs, such as the Grafana OnCall API, some routes return 50 records per page. The page size is not configurable. In my opinion, a limit of 250 records is far too conservative. |
Beta Was this translation helpful? Give feedback.
-
Check out the GitHub GraphQL API for an application in GraphQL for this. It might be nice to give the GraphQL mode access to pagination. |
Beta Was this translation helpful? Give feedback.
-
My eventual solution: Fivetran + neon postgresql database (both have a free tier) Works wonders |
Beta Was this translation helpful? Give feedback.
-
There are many cases where the API that's being called is an internal API so it should be down to the developer to choose what the max number of pages is, can the limit be removed from max pages? |
Beta Was this translation helpful? Give feedback.
-
Also facing the 5 pages limitation problem on an internal API. |
Beta Was this translation helpful? Give feedback.
-
Same problem with pagination. 5 is very very low |
Beta Was this translation helpful? Give feedback.
-
Background and current status of pagination feature ( Nov 2024 )Pagination feature was introduced in infinity backend parser an year ago as an experimental/beta/undocumented feature. As there are different types of pagination and much complexities behind handling them, still we aren't in a position to make it out of beta. The complexities include how to handle error in one of the pages, when to stop the pagination, how to handle partial data, how to handle no data vs error, how to stop racing condition, making parallel requests for paginated queries to improve the performance etc. Though this feature is in beta, We love the enthusiasm of the community who tried the pagination feature and providing continuous feedback and exploring the potentials of the infinity plugin. Maximum number of pages option & issues behindWhen the pagination feature was introduced, I strongly believed that getting paginated results in grafana is a unusual/unconventional use case. With Grafana's use cases user should query aggregated results instead of pulling every data and post processing/filtering/aggregation in the grafana where possible. Also loading large number of results with pagination into grafana's memory will put additional stress to grafana server. If one of the poor query triggers heavy pagination, it will affect all other grafana users in that instance. While considering the pagination, we do consider not only the requests coming from dashboards but also other cron jobs such as alerting, recorded queries etc. Increasing the max pagination will increase the grafana server memory/cpu in such cases as well. I agree that there are workarounds that a user can trigger multiple paginated queries via options such as repeat panel etc. That still doesn't justify the needs to increase the max pagination size. Path/Options forwardThough this is beta/experimental feature, we understand that pagination is important for many users and some use cases. Also removing the limitation on max pagination is also crucial for some users. Note We haven't ignored the option for max page customisation. Instead, we are exploring safer options such as setting the option via environment variable so that grafana admins can take informed decision about this configuration. This will also protect our grafana cloud and partner cloud hosted grafana environments. Also we have prioritised other important features such as supporting oAuth scenarios, making the backend parser as default, improving the documentation etc to make this plugin better. Also we are running low in bandwidth to implement/enhance the pagination. But we are open for enhancement once we have enough use case information around this. Looking for feedback & use-casesThe more use cases we can gather from the community, the better we are able to design and prioritise a solution for the pagination feature. Feel free to provide the use-cases and feedback in this discussion. |
Beta Was this translation helpful? Give feedback.
-
My use case: I need to create a "scorecard" or "status" visualization to show policy compliance for a set of devices - a kind of table with devices in the rows and "device policies" (rules that check aspects of a device configuration) in the columns (fields). If a device is compliant for a policy, the table cell should be green. If the device is non-compliant, the table cell should be red. The data source for the required visualization is the configuration management application's REST API. The REST API request uses a device ID in the URL to get a response containing a list of non-compliant policies for that device. I have 50 devices (in a dashboard variable). But given the nature of the REST API endpoint and current Grafana/Infinity limitations, I will need to configure the Grafana panel with 50 separate hard-coded REST API queries and then use Transformations to merge the results together. This is not good. Maybe I am missing something??? If I was trying to get this data with an independent script, I would loop through the variable device list to construct the REST API query URLs, not hardcode anything. Anyway, I was stumped about how to do this with Infinity until I came across this pagination feature which got me excited until I realized it's still in beta (and has a limitation of 5 pages). If there's another way to do this, please let me know. Thanks. |
Beta Was this translation helpful? Give feedback.
-
I am using Grafana from a DevOps perspective:
Based on my personal need and from what I can read from other people's comments, it doesn't seem like pagination is the main need, but the ability to run multi-step API calls, with one step consisting of parallel/looping requests that is later merged/aggregated. It just so happens that the pagination functionality solves this problem, with the limitation of only being able to run 5 requests. For my use case the data returned is not a lot per request, and I would much rather have Grafana be responsible for the aggregation than having to also set up prometheus/database/whatever and add something additional I need to maintain. |
Beta Was this translation helpful? Give feedback.
-
Hello,
I had the same problem I don’t know how I retrieve data for multiple
workflow runs knowing that each one has a different id. I just know that
variable can be put as part of URL using /$id_job as example. But How to
loop over existing IDs of worlkflows no ideas.
Good luck
Abdessalam BENAYYAD
…On Mon 10 Feb 2025 at 14:42, Paul Coada ***@***.***> wrote:
I am using Grafana from a DevOps perspective:
- I perform a request towards a build project to get a historical list
of builds
- Each build consists of parallel jobs. I want to visualize each job
for each build, and I can only retrieve the job status by performing a
request to that particular build
Build Job 1 Job 2
# 1 ✅ ✅
# 2 ✅ ✅
... ... ...
Based on my personal need and from what I can read from other people's
comments, it doesn't seem like *pagination* is the main need, but the
ability to run multi-step API calls, with one step consisting of
parallel/looping requests that is later merged/aggregated. It just so
happens that the pagination functionality solves this problem, with the
limitation of only being able to run 5 requests. For my use case the data
returned is not a lot per request, and I would much rather have Grafana be
responsible for the aggregation than having to also set up
prometheus/database/whatever and add something additional I need to
maintain.
—
Reply to this email directly, view it on GitHub
<#601 (comment)>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/AS3UFM3TECSJASIPAOQXQ732PCUD3AVCNFSM6AAAAAAYM2NMZ2VHI2DSMVQWIX3LMV43URDJONRXK43TNFXW4Q3PNVWWK3TUHMYTEMJRHE4DKNA>
.
You are receiving this because you commented.Message ID:
<grafana/grafana-infinity-datasource/repo-discussions/601/comments/12119854
@github.com>
|
Beta Was this translation helpful? Give feedback.
-
This 5-page limit is severe making this product unusable. I have 13 pages of 100 in my data currently. Using Loki connectors, I have 100s of thousands of lines of data going through hourly. yet this cannot even handle more than 5 pages. Frustrating. |
Beta Was this translation helpful? Give feedback.
-
I don't understand why a feature sabotages itself by this limitation to 5 requests in one shot. It doesn't make any sense as the developer of the dashboard is responsible for the utilization of the API endpoint and should do anything to prevent DDOS or resource overutilization which might still be actually possible for the dashboard user anyway. |
Beta Was this translation helpful? Give feedback.
-
Pagination should be a JavaScript/Lua/Starlark/anything scriptable so we can accommodate to whatever weird API we are dealing with. Hundreds of combinations from forms with little documentation isn't the way to go, IMHO. And I fully support the others when they say that the feature sabotages itself. The current iteration of pagination isn't useful. As a final note, to the maintainer that keeps replying "you are using the wrong tool for the job" to every single one of us that complaints about the feature, they should take a look at Grafana and ask "what is Grafana even about" bc he is clearly lost on this one. |
Beta Was this translation helpful? Give feedback.
-
Hi @yesoreyeram , we are using offset pagination which is working absolutely fine, the response from our api is parsed with "Documents" key: jsonData = { but the results are displayed in a single row the paginatinated api call as below.
previously before pagination our result used to be like below: what we are missing here, can we achieve same for pagination thing we aslo below issue: Status: 500. Message: error while performing the infinity query. unable to merge fields due to different fields |
Beta Was this translation helpful? Give feedback.
-
Hello @yesoreyeram thanks for adding pagination!!
|
Beta Was this translation helpful? Give feedback.
-
Hi, I had the same problem, basically the pagination was separating my json into two different arrays, so I used a transformation combo to get around the problem |
Beta Was this translation helpful? Give feedback.
-
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
Available from: Infinity version 2.0.0
Supported types: JSON
Supported parsers: Backend
Pagination
When calling an API, if the underlying system have lots of results typically the server will send responses in multiple pages.
Pagination in Infinity
Introducing pagination of API response in Infinity 2.0. Prior to infinity version 2.0.0, you can only one page at a time. To call multiple pages and consolidate, you might be adding multiple queries manually and use merge transformation.
Types of Pagination
In the modern API world, pagination is implemented in different ways. Following are the common pagination mechanisms supported in infinity
Offset based pagination
TODO: yet to be documented
Page number based pagination
TODO: yet to be documented
Cursor based pagination
TODO: yet to be documented
Iterating URLs in a loop
Apart from the regular pagination methods mentioned above, From infinity 2.0, you have the ability to iterate the URLs based on comma separated values.
For example, we would like to call 3 different pokemons API items and show in a single result. We will be using following three URL.
As you see, we have three different URLs with 3 different paths. So I am going to to parameterise this as follows.
Now in the infinity pagination, I can instruct it to replace
{{ pokemon_name }}
part of the URL withbulbasaur,ivysaur,venusaur
. Under the hood, infinity will split the values by,
and then replace{{ pokemon_name }}
with each item in the list and make the API call.Below screenshot is an example of how to use it.
When used with dashboard variables, you can replace the hardcoded list of items to point a variable. Example: When you have a multi-value variable called
pokemon_id
, you can refer it as${pokemon_id:csv}
in the list value.Limitation
Number of maximum pages per query is limited to 5. This is to avoid resource exhaustion and DDOSing of the target system.
Beta Was this translation helpful? Give feedback.
All reactions