Skip to main content
RapidDev - Software Development Agency
flutterflow-integrationsFlutterFlow API Call

Serpstat

Connect FlutterFlow to Serpstat by creating an API Group with base URL https://api.serpstat.com/v4 and a ?token= query parameter, then using a single POST call whose JSON body sets the 'method' field to select the report type — this is Serpstat's JSON-RPC design. Route the token through a Firebase Cloud Function proxy to keep it off the client, and cache results in App State to stay within monthly credit limits.

What you'll learn

  • How Serpstat's JSON-RPC pattern works — one endpoint, many reports selected by the 'method' body field
  • How to create a FlutterFlow API Group and a single POST API Call with variable method and params
  • How to parse Serpstat's nested JSON response using JSON Path ($.result.data[*])
  • How to proxy the Serpstat token through a Firebase Cloud Function with 429 backoff
  • How to cache keyword data in App State to stay within monthly Serpstat credit limits
Book a free consultation
4.9Clutch rating
600+Happy partners
17+Countries served
190+Team members
Intermediate16 min read45 minutesMarketingLast updated July 2026RapidDev Engineering Team
TL;DR

Connect FlutterFlow to Serpstat by creating an API Group with base URL https://api.serpstat.com/v4 and a ?token= query parameter, then using a single POST call whose JSON body sets the 'method' field to select the report type — this is Serpstat's JSON-RPC design. Route the token through a Firebase Cloud Function proxy to keep it off the client, and cache results in App State to stay within monthly credit limits.

Quick facts about this guide
FactValue
ToolSerpstat
CategoryMarketing
MethodFlutterFlow API Call
DifficultyIntermediate
Time required45 minutes
Last updatedJuly 2026

Build an Affordable SEO App with Serpstat's Single-Endpoint API in FlutterFlow

Serpstat is the value pick in the SEO API market — it offers keyword research, domain analytics, and backlink data at price points well below Ahrefs (which requires an Enterprise plan) or SEMrush (which charges per unit on top of a seat subscription). For FlutterFlow developers building an SEO dashboard or keyword research companion app, Serpstat's lower cost makes it the practical choice for apps where the API will be called frequently.

What sets Serpstat apart architecturally is its JSON-RPC design: there is exactly one API endpoint (https://api.serpstat.com/v4), and you select which report to fetch by setting a 'method' field in the POST body — for example, 'SerpstatDomainProcedure.getDomainKeywords' for keyword data or 'SerpstatDomainProcedure.getDomainInfo' for domain metrics. The 'params' body field carries the report parameters (domain, se — search engine/country database). This pattern is fundamentally different from the other SEO APIs in this category, which use distinct URL paths per report. In FlutterFlow it means you build ONE API Call and control which report runs by changing the body variables — a clean, reusable design.

Authentication uses a token passed as a ?token= query parameter appended to the URL. Like SEMrush's ?key= pattern, query strings appear in network logs and are embedded in the compiled app binary, making proxy routing essential. Serpstat also enforces both a per-second request rate limit and a monthly credit/unit quota — so the same unit-conservation pattern applies: cache in App State, refresh on demand, add retry backoff in the proxy for 429 responses.

Integration method

FlutterFlow API Call

FlutterFlow connects to Serpstat through a single API Group pointing at https://api.serpstat.com/v4, with the API token passed as a ?token= query parameter. Every Serpstat report is fetched via the same POST endpoint — the report type is selected by setting a 'method' field in the JSON request body (JSON-RPC pattern). A Firebase Cloud Function proxy holds the token server-side; FlutterFlow calls the proxy URL with the method and params, and the response JSON is parsed with JSON Path and bound to widgets.

Prerequisites

  • A Serpstat account with API access enabled (API is available on paid Serpstat plans; verify which plan includes API credits)
  • Your Serpstat API token from the Serpstat dashboard → Profile → API
  • A FlutterFlow project (free or paid) with a screen ready to display keyword or domain data
  • A Firebase project for the Cloud Function proxy that holds the Serpstat token and handles 429 retry logic
  • Basic familiarity with FlutterFlow's API Calls panel; understanding of POST requests with JSON bodies is helpful

Step-by-step guide

1

Deploy a Firebase Cloud Function proxy with 429 backoff

Serpstat's token goes in the URL query string (?token=...), which means it appears in HTTP access logs at any intermediate point and is embedded in the compiled Flutter binary if placed in a FlutterFlow API Call variable. The Cloud Function proxy solves this and also provides the 429 backoff that FlutterFlow API Calls cannot do natively — FlutterFlow has no built-in retry mechanism, so hammering Serpstat when the per-second limit is exceeded would silently fail without a retry. Create an HTTP Cloud Function. The function receives the method and params from FlutterFlow in its POST body, reads the token from process.env.SERPSTAT_TOKEN, builds the Serpstat v4 URL with the token appended, and POSTs the JSON-RPC body to it. Add simple 429 retry logic: if Serpstat returns 429, wait 1 second and retry once before returning the error to FlutterFlow. Set the token: firebase functions:config:set serpstat.token='YOUR_TOKEN'. Add Access-Control-Allow-Origin: * headers for FlutterFlow web builds. Deploy with firebase deploy --only functions. Test by POSTing {"method": "SerpstatDomainProcedure.getDomainInfo", "params": {"domain": "example.com", "se": "g_us"}} to your function URL and confirming you get a JSON response with result.data.

index.js
1// Firebase Cloud Function proxy for Serpstat (functions/index.js)
2const functions = require('firebase-functions');
3const axios = require('axios');
4
5const sleep = (ms) => new Promise(resolve => setTimeout(resolve, ms));
6
7exports.serpstatProxy = functions.https.onRequest(async (req, res) => {
8 res.set('Access-Control-Allow-Origin', '*');
9 res.set('Access-Control-Allow-Methods', 'POST, OPTIONS');
10 res.set('Access-Control-Allow-Headers', 'Content-Type');
11 if (req.method === 'OPTIONS') { res.status(204).send(''); return; }
12 if (req.method !== 'POST') {
13 return res.status(405).json({ error: 'POST required' });
14 }
15
16 const token = process.env.SERPSTAT_TOKEN;
17 const method = req.body?.method;
18 const params = req.body?.params || {};
19
20 if (!method) {
21 return res.status(400).json({ error: 'method is required' });
22 }
23
24 const url = `https://api.serpstat.com/v4?token=${token}`;
25 const body = { id: 1, method, params };
26
27 const doRequest = async (attempt) => {
28 try {
29 const response = await axios.post(url, body, {
30 headers: { 'Content-Type': 'application/json' },
31 timeout: 15000
32 });
33 return response.data;
34 } catch (err) {
35 if (err.response?.status === 429 && attempt === 1) {
36 await sleep(1000);
37 return doRequest(2);
38 }
39 throw err;
40 }
41 };
42
43 try {
44 const data = await doRequest(1);
45 res.json(data);
46 } catch (err) {
47 const status = err.response?.status || 500;
48 res.status(status).json({ error: err.message });
49 }
50});

Pro tip: The Serpstat JSON-RPC spec requires an 'id' field in the request body (any integer). Setting id: 1 is fine — Serpstat echoes it back in the response and FlutterFlow ignores it.

Expected result: The Cloud Function is deployed and returns Serpstat JSON with result.data when you POST a valid method and params to its URL.

2

Create the Serpstat API Group in FlutterFlow

In FlutterFlow, navigate to API Calls in the left nav. Click + Add → Create API Group. Name it Serpstat. In the Base URL field, paste your Cloud Function URL: https://us-central1-YOUR_PROJECT.cloudfunctions.net/serpstatProxy. Since your proxy handles authentication internally, you do not need any Authorization headers at the group level. However, you may want to add an optional X-App-Key header with a static secret UUID that your Cloud Function checks — this restricts your proxy so only your FlutterFlow app can call it, rather than anyone who discovers the Cloud Function URL. Save the group. The Serpstat group now appears in the left nav, ready for API Call definitions. The key insight here is that unlike Ahrefs (separate calls per endpoint) or Moz (one endpoint, one purpose), you will create just ONE API Call inside this group — because Serpstat's single URL handles all report types via the method body field.

Pro tip: Name the group 'Serpstat' (not 'SEO API' or 'Analytics'), since FlutterFlow shows the group name in action dropdowns. A clear name makes it easy to identify when setting up button actions later.

Expected result: The Serpstat API Group is saved and visible in the left nav with your Cloud Function URL as the base URL.

3

Add the single multi-purpose POST API Call

Because Serpstat uses a JSON-RPC design, you only need one API Call. The method field in the body determines which report runs. You will pass method and params as FlutterFlow body Variables, making this call reusable across different screens with different report needs. Click + inside the Serpstat group → Create API Call. Name it Serpstat Query. Set the HTTP Method to POST. Set the Body Type to JSON. Go to the Variables tab and add: - method (String, required) — e.g. 'SerpstatDomainProcedure.getDomainInfo' - domain (String, required) — the domain to query - se (String, default: g_us) — the search engine/country database (g_us, g_uk, g_de, etc.) - limit (Integer, default: 100) — max rows of keyword data to return In the Body field, use this JSON template: {"method": "{{method}}", "params": {"domain": "{{domain}}", "se": "{{se}}", "size": {{limit}}}} Note: for keyword methods (SerpstatKeywordProcedure.getKeywordInfo), replace 'domain' in params with 'keyword'. You can handle this by adding a keyword variable and building two API Calls (one for domain methods, one for keyword methods) — or use a single flexible call with both variables and let the proxy pick the right one. Switch to Response & Test. Fill in method=SerpstatDomainProcedure.getDomainInfo, domain=example.com, se=g_us. Run the test. The JSON response will have a result.data object with fields like keyword_count, traff, traff_cost. Click Generate JSON Paths. Map: $.result.data.keyword_count → keywordCount, $.result.data.traff → estimatedTraffic, $.result.data.traff_cost → trafficCost.

serpstat_api_call.json
1// API Call POST body template
2{
3 "method": "{{method}}",
4 "params": {
5 "domain": "{{domain}}",
6 "se": "{{se}}",
7 "size": {{limit}}
8 }
9}
10
11// Common Serpstat methods to use as the 'method' variable:
12// Domain reports:
13// SerpstatDomainProcedure.getDomainInfo — overall domain metrics
14// SerpstatDomainProcedure.getDomainKeywords — organic keyword list
15// SerpstatDomainProcedure.getCompetitors — domain competitors
16// Keyword reports:
17// SerpstatKeywordProcedure.getKeywordInfo — keyword volume + CPC
18// SerpstatKeywordProcedure.getRelatedKeywords — related keywords list
19
20// JSON Paths for getDomainInfo response:
21// keywordCount → $.result.data.keyword_count
22// estimatedTraff → $.result.data.traff
23// trafficCost → $.result.data.traff_cost
24// visibilityScore → $.result.data.visible_percentage

Pro tip: The 'se' parameter is the Google regional database code: g_us (US), g_uk (UK), g_de (Germany), g_fr (France), g_au (Australia), etc. Expose it as a dropdown in your UI so users can switch regional data.

Expected result: The Serpstat Query API Call is saved. The test panel returns domain metrics JSON when called with getDomainInfo. JSON Paths for keyword count and traffic are generated.

4

Parse nested JSON results and bind to widgets

Serpstat's responses nest data inside result.data — for domain methods it is a single object, and for keyword list methods (getDomainKeywords, getRelatedKeywords) it is an array at $.result.data[*]. FlutterFlow's JSON Path tool handles both, but you need to configure your JSON Paths correctly for each case. For domain overview data (getDomainInfo): the JSON Path $.result.data.keyword_count extracts a single integer. Bind it directly to a Text widget on your dashboard card. For keyword list data (getDomainKeywords): the JSON Path $.result.data[*].keyword extracts all keyword strings as a list, and $.result.data[*].traff extracts the corresponding traffic values. In FlutterFlow, create a custom Data Type called SerpstatKeyword with fields: keyword (String), traff (int), cost (double), keyword_length (int), concurrency (int). Use the API Call's JSON Path list extraction to generate a list of SerpstatKeyword items, then bind the list to a ListView whose list tile widgets display keyword name and volume. On your domain overview screen, add a Row with three metric Cards: Keyword Count, Estimated Traffic, and Traffic Cost Value. Bind each to the relevant App State variable populated by the API Call action. For the keyword list screen, add a ListView bound to the list returned by the getDomainKeywords call, with each item showing the keyword and its traffic estimate. Add a search/filter bar above the ListView so users can narrow the keyword list without making a new API call.

Pro tip: When using list JSON Paths ($.result.data[*].keyword), FlutterFlow generates separate list extractors for each field. Create matching index lists and zip them together in your Data Type mapping — or create a Custom Action that parses the raw response JSON into your Data Type list in a single pass for cleaner code.

Expected result: Domain metric cards show keyword count and estimated traffic from the App State. A keyword ListView shows individual keywords with their traffic values from the getDomainKeywords call.

5

Wire the full action flow and handle rate limits

Now connect all the pieces into a working app flow. On your main screen, add a TextField for domain input and a Search button. In the Search button's Actions panel: 1. Validate the TextField is not empty. 2. Set App State variable isLoading = true. 3. Backend/API Call → Serpstat → Serpstat Query, with method = 'SerpstatDomainProcedure.getDomainInfo', domain = TextField value, se = currently selected database, limit = 100. 4. On success: update App State with the parsed JSON Path values (keywordCount, estimatedTraffic, trafficCost). Set isLoading = false. 5. On error: show a Dialog — if the error is a 429 response, display 'Serpstat rate limit reached — please wait a moment.' If it's a 401, display 'Invalid token — check your Serpstat API configuration.' For unit conservation, add a lastSearched App State variable (String, stores the last-queried domain). At the start of the Search action, check if the domain TextField matches lastSearched AND the App State metrics are not null — if both are true, skip the API call and display the cached App State values with a toast 'Showing cached result'. This saves a credit on repeated searches for the same domain. If you'd rather skip the custom action and proxy setup and have a FlutterFlow expert wire this for you, RapidDev's team builds integrations like this every week — free scoping call at rapidevelopers.com/contact.

Pro tip: Serpstat credits and per-second rate limits are both active simultaneously. The per-second limit fires first (429); if you exhaust your monthly credits, you will receive an error in the result.error field of the JSON response rather than an HTTP error code — check for this field in your action flow.

Expected result: The full search flow works end to end: user enters a domain, taps Search, the proxy calls Serpstat, JSON is parsed, and domain metrics appear on screen. Cached results display on repeat searches without consuming additional credits.

Common use cases

Keyword research and volume lookup tool

Build a keyword research app where a user types a search phrase, selects a country database (US, UK, DE, etc.), and sees monthly volume, CPC, competition level, and related keyword suggestions from Serpstat. The app uses the SerpstatKeywordProcedure.getKeywordInfo method in the POST body and displays results in a card list. Results are stored in a local Supabase table for later review, avoiding repeated API calls for recently researched keywords.

FlutterFlow Prompt

A keyword research app where a user types a keyword and selects a country, then sees monthly search volume, CPC, and competition level from Serpstat in a list of cards.

Copy this prompt to try it in FlutterFlow

Domain keyword and traffic overview dashboard

Build an internal SEO monitoring app that shows a domain's estimated organic keyword count and visibility score from Serpstat. Users enter a domain, the app calls SerpstatDomainProcedure.getDomainInfo via the proxy, and displays keyword_count, traff, and traff_cost on metric cards. A refresh button at the top right re-triggers the API call and updates the cached App State value.

FlutterFlow Prompt

An SEO dashboard app where a user enters a domain and sees its organic keyword count, estimated traffic, and traffic cost value from Serpstat on a metrics card.

Copy this prompt to try it in FlutterFlow

Competitor keyword gap analysis screen

Build a comparison screen where a user enters two domains and the app fetches getDomainInfo for each using two sequential API calls through the same Serpstat proxy. The results display side by side on a split-card layout showing keyword count and traffic for both domains, highlighting the domain with more organic presence. The single-endpoint design means both calls use the exact same FlutterFlow API Call — only the params.domain variable differs.

FlutterFlow Prompt

A competitor SEO comparison app that shows two domains side by side with their organic keyword count and estimated traffic from Serpstat.

Copy this prompt to try it in FlutterFlow

Troubleshooting

API returns status 200 but result.data is empty or null

Cause: Serpstat returns status 200 even for 'no data' results. This happens when the domain has no indexed keywords in the selected search engine database ('se' parameter), or when the account's monthly credits are exhausted. Serpstat also returns error details in a result.error field rather than using HTTP error codes.

Solution: Check the result.error field in the JSON response in your Cloud Function logs. If it contains a credits error, your monthly quota is exhausted. If it contains 'no data', try a different 'se' (e.g. change g_uk to g_us). If credits are the issue, wait for the next billing cycle or upgrade your Serpstat plan.

429 Too Many Requests — API calls failing during testing

Cause: Serpstat enforces a per-second request rate limit. Rapid consecutive taps on the Search button, or a widget that triggers re-fetch on every rebuild, can exceed this limit even with a modest request volume.

Solution: Ensure the Cloud Function proxy has the 1-second retry backoff implemented as shown in Step 1. In FlutterFlow, disable the Search button while an API call is in flight (bind its disabled state to the isLoading App State variable) to prevent rapid duplicate taps. If the ListView refetches on scroll, move the data source from a widget API call to App State.

XMLHttpRequest error in FlutterFlow Run mode when testing the API Call

Cause: CORS error. If the API Group's base URL points to api.serpstat.com instead of your Cloud Function, the browser blocks the cross-origin POST request. FlutterFlow's web-based Run mode enforces CORS; native mobile builds do not.

Solution: Confirm the API Group base URL is your Cloud Function URL (https://us-central1-YOUR_PROJECT.cloudfunctions.net/serpstatProxy). If you set it to api.serpstat.com for quick testing, update it to the proxy URL. The Cloud Function adds the necessary CORS headers so web runs work correctly.

JSON Path $.result.data[*].keyword returns no results in FlutterFlow

Cause: For getDomainInfo, result.data is an object (not an array), so the [*] wildcard returns nothing. The [*] syntax is only correct for list methods like getDomainKeywords or getRelatedKeywords.

Solution: Use method-appropriate JSON Paths: $.result.data.keyword_count (no wildcard) for getDomainInfo, and $.result.data[*].keyword (with wildcard) for getDomainKeywords. Create separate API Call definitions or separate JSON Path sets for each method type. The FlutterFlow API Call Response & Test tab will show you the exact shape of the response when you run a test.

Best practices

  • Never put the Serpstat token in a FlutterFlow query variable — the ?token= value is embedded in the compiled Dart binary and appears in server access logs. Always proxy through a Firebase Cloud Function with the token in environment variables.
  • Implement 429 backoff in the Cloud Function proxy (not in FlutterFlow) since FlutterFlow API Calls have no built-in retry mechanism — one second of sleep before retrying is usually enough to satisfy the per-second rate limit.
  • Cache the last domain-queried result in App State and skip re-fetching if the user searches the same domain again within a session — Serpstat credits are metered, and repeated identical calls waste quota.
  • Use the Serpstat dashboard to monitor your monthly credit consumption regularly, especially during app development when you may be testing frequently.
  • Expose the 'se' (search engine/country) parameter as a dropdown in your UI so users can switch regional databases without code changes — this is one of Serpstat's most useful features for international SEO teams.
  • Check result.error in the JSON response body in addition to HTTP status codes — Serpstat returns 200 with an error in the payload for credit exhaustion and other quota issues.
  • Use a single reusable Serpstat Query API Call for all report types (vary only the method and params variables) rather than creating separate API Calls per method — this keeps your API Calls panel clean and the proxy logic unified.

Alternatives

Frequently asked questions

What makes Serpstat's API different from Ahrefs or SEMrush?

Serpstat uses a JSON-RPC design: one endpoint URL, and you select the report by setting a 'method' field in the JSON POST body. Ahrefs uses separate URL paths per endpoint with a Bearer header, and SEMrush uses separate URL parameters with a query-string key and returns CSV. Serpstat's single-endpoint design means you configure one FlutterFlow API Call and reuse it for all report types by varying the body variables.

Is there a free tier for the Serpstat API?

Serpstat API access is available on paid Serpstat plans. There is no permanently free API tier, though Serpstat offers trial periods. Check the current plan pricing at serpstat.com/plans — API credit allotments vary by plan level, and the per-API-call cost varies by report type. Domain overview calls are generally cheaper than large keyword list exports.

Can I use Serpstat for both keyword research and domain analytics in the same FlutterFlow app?

Yes — this is one of Serpstat's advantages. Because all report types share the same endpoint, your single FlutterFlow API Call can fetch domain metrics, keyword lists, competitor domains, and related keyword suggestions simply by changing the 'method' body variable. Build different screens that all use the same Serpstat Query API Call with different method and params values.

What does the 'se' parameter mean in Serpstat requests?

The 'se' (search engine) parameter selects the regional Google index to query — for example, g_us for Google US, g_uk for Google UK, g_de for Google Germany. Serpstat stores separate keyword databases per regional index, so the keyword volumes and domain rankings it returns are specific to that country's Google results. Always set 'se' to match your target market.

Why is my Serpstat proxy returning 200 but the data is empty?

Serpstat returns HTTP 200 even when there is no data for a domain or when credits are exhausted. Check the result.error field inside the JSON response body — if credits are exhausted, this field contains an error message. If result.error is null but result.data is also empty, the domain has no indexed keywords in the selected regional database. Try switching the 'se' parameter to a different regional index.

RapidDev

Talk to an Expert

Our team has built 600+ apps. Get personalized help with your project.

Book a free consultation

Integrations are where projects stall

We wire FlutterFlow integrations like this one every week — auth, webhooks, edge cases included. Fixed-price builds from $13K, delivered in 6–10 weeks.

Talk to an integration engineer

We put the rapid in RapidDev

Need a dedicated strategic tech and growth partner? Discover what RapidDev can do for your business! Book a call with our team to schedule a free, no-obligation consultation. We'll discuss your project and provide a custom quote at no cost.