How to Build a Keyword Research Tool with Autocomplete and People Also Ask Data
Learn how to build a keyword research tool with autocomplete suggestions and People Also Ask data. Use Python to collect keyword ideas, questions, intent signals, and export results to CSV.
Quick answer: You can build a keyword research tool by combining autocomplete suggestions with People Also Ask questions. Autocomplete helps expand long-tail keyword ideas, while People Also Ask reveals question-based intent. A SERP API can collect these search signals, and Python can normalize them into a CSV file for SEO planning, content briefs, or AI workflows.
Keyword research is not only about search volume.
When people search, they reveal intent through the words they type, the suggestions they see, and the questions shown around a topic.
Two useful sources are:
-
Autocomplete data: search suggestions based on a seed keyword
-
People Also Ask data: question-style results related to a query
Together, they can help you find long-tail keywords, FAQ ideas, content angles, and search intent patterns.
For the data layer, you can use Talordata SERP API or another SERP API that returns structured search results. Talordata’s product page describes structured real-time search data across Google and major search engines, with JSON / HTML output and geo-targeting support.
Why Autocomplete and People Also Ask Matter
Autocomplete and People Also Ask answer different questions.
|
Data source |
What it helps you find |
|
Autocomplete |
Long-tail keyword variations users may type |
|
People Also Ask |
Questions users may ask before clicking a result |
|
Organic snippets |
How ranking pages frame the topic |
|
Related searches |
Additional topic clusters |
For example, from the seed keyword:
serp api
Autocomplete may return ideas like:
serp api pricing
serp api python
serp api for seo
serp api alternatives
serp api for ai agents
People Also Ask may return questions like:
What is a SERP API?
How do SERP APIs work?
Is it legal to scrape search results?
What is the best API for Google search results?
Autocomplete gives you what people may type. People Also Ask gives you what people may want to understand.
What We Will Build
We will create a Python workflow:
Seed keyword
→ Collect autocomplete suggestions
→ Collect People Also Ask questions
→ Normalize keyword ideas
→ Classify search intent
→ Export results to CSV
The final CSV can include:
|
Field |
Meaning |
|
|
The original keyword |
|
|
The collected keyword or question |
|
|
Autocomplete or PAA |
|
|
Informational, commercial, technical, local, or general |
|
|
Number of words in the keyword |
|
|
Suggested content format |
|
|
Collection timestamp |
Step 1: Set Environment Variables
Use environment variables instead of hardcoding credentials.
export TALORDATA_API_KEY="your_api_key_here"
export TALORDATA_SERP_ENDPOINT="your_talordata_serp_endpoint_here"
On Windows PowerShell:
$env:TALORDATA_API_KEY="your_api_key_here"
$env:TALORDATA_SERP_ENDPOINT="your_talordata_serp_endpoint_here"
Install the package:
pip install requests
Use the endpoint and parameters shown in your Talordata dashboard or API documentation. Talordata’s docs provide query parameter sections for SERP API workflows.
Step 2: Create a Request Helper
Keep the request layer separate from parsing logic. This makes the script easier to adjust later.
import os
import requests
def require_env(name):
value = os.getenv(name)
if not value:
raise RuntimeError(f"Missing required environment variable: {name}")
return value
TALORDATA_API_KEY = require_env("TALORDATA_API_KEY")
TALORDATA_SERP_ENDPOINT = require_env("TALORDATA_SERP_ENDPOINT")
def call_serp_api(payload):
headers = {
"Authorization": f"Bearer {TALORDATA_API_KEY}",
"Content-Type": "application/json"
}
response = requests.post(
TALORDATA_SERP_ENDPOINT,
json=payload,
headers=headers,
timeout=30
)
response.raise_for_status()
return response.json()
Some APIs use GET instead of POST, or pass the API key as a query parameter. If your setup is different, only update this helper.
Step 3: Collect Autocomplete Suggestions
Autocomplete responses may use different field names, so the parser below supports several common formats.
def fetch_autocomplete(seed_keyword, location="United States", language="en"):
payload = {
"engine": "google_autocomplete",
"q": seed_keyword,
"location": location,
"hl": language,
"output": "json"
}
return call_serp_api(payload)
def extract_autocomplete_keywords(response_json):
raw_items = (
response_json.get("suggestions")
or response_json.get("autocomplete_results")
or response_json.get("completion_results")
or []
)
keywords = []
for item in raw_items:
if isinstance(item, str):
keywords.append(item)
elif isinstance(item, dict):
keyword = item.get("value") or item.get("suggestion") or item.get("keyword")
if keyword:
keywords.append(keyword)
return keywords
If your API uses another engine name, such as autocomplete or google_suggest, change the engine value.
Step 4: Collect People Also Ask Questions
People Also Ask data usually comes from a regular Google search response. It may appear under keys such as related_questions, people_also_ask, or paa_results.
def fetch_google_search(query, location="United States", language="en", country="us"):
payload = {
"engine": "google",
"q": query,
"location": location,
"hl": language,
"gl": country,
"num": 10,
"output": "json"
}
return call_serp_api(payload)
def extract_paa_questions(response_json):
raw_items = (
response_json.get("related_questions")
or response_json.get("people_also_ask")
or response_json.get("paa_results")
or []
)
questions = []
for item in raw_items:
if isinstance(item, str):
questions.append(item)
elif isinstance(item, dict):
question = item.get("question") or item.get("title")
if question:
questions.append(question)
return questions
PAA questions are useful for FAQ sections, explainer articles, comparison pages, and content briefs.
Step 5: Classify Search Intent
A simple rule-based classifier is enough for a first version.
def classify_intent(keyword):
text = keyword.lower()
if any(word in text for word in ["what", "why", "how", "guide", "tutorial"]):
return "informational"
if any(word in text for word in ["best", "top", "vs", "alternative", "compare"]):
return "commercial"
if any(word in text for word in ["price", "pricing", "cost", "free trial"]):
return "commercial"
if any(word in text for word in ["api", "python", "docs", "integration", "example"]):
return "technical"
if any(word in text for word in ["near me", "local", "map", "maps"]):
return "local"
return "general"
This will not be perfect, but it gives you a useful first grouping layer.
Step 6: Suggest Content Angles
Now add a simple rule to recommend content formats.
def suggest_content_angle(keyword, source):
intent = classify_intent(keyword)
if source == "paa":
return "FAQ section or explainer paragraph"
if intent == "technical":
return "Developer tutorial"
if intent == "commercial":
return "Comparison or buying guide"
if intent == "local":
return "Local SEO landing page or local report"
if intent == "informational":
return "Educational blog post"
return "Topic cluster supporting page"
This makes the output more useful for SEO and content teams.
Step 7: Export Keyword Ideas to CSV
import csv
from datetime import datetime, timezone
CSV_COLUMNS = [
"seed_keyword",
"keyword",
"source",
"intent",
"word_count",
"content_angle",
"collected_at"
]
def clean_text(value):
if not value:
return ""
return " ".join(str(value).split())
def build_rows(seed_keyword, keywords, source):
collected_at = datetime.now(timezone.utc).isoformat()
rows = []
for keyword in keywords:
cleaned = clean_text(keyword)
if not cleaned:
continue
rows.append({
"seed_keyword": seed_keyword,
"keyword": cleaned,
"source": source,
"intent": classify_intent(cleaned),
"word_count": len(cleaned.split()),
"content_angle": suggest_content_angle(cleaned, source),
"collected_at": collected_at
})
return rows
def dedupe_rows(rows):
seen = set()
unique_rows = []
for row in rows:
key = row["keyword"].lower()
if key in seen:
continue
seen.add(key)
unique_rows.append(row)
return unique_rows
def export_to_csv(rows, filename="keyword_research_results.csv"):
if not rows:
print("No keyword ideas found.")
return
with open(filename, mode="w", newline="", encoding="utf-8") as file:
writer = csv.DictWriter(file, fieldnames=CSV_COLUMNS)
writer.writeheader()
writer.writerows(rows)
print(f"Exported {len(rows)} keyword ideas to {filename}")
Complete Python Example
import os
import csv
import requests
from datetime import datetime, timezone
CSV_COLUMNS = [
"seed_keyword",
"keyword",
"source",
"intent",
"word_count",
"content_angle",
"collected_at"
]
def require_env(name):
value = os.getenv(name)
if not value:
raise RuntimeError(f"Missing required environment variable: {name}")
return value
TALORDATA_API_KEY = require_env("TALORDATA_API_KEY")
TALORDATA_SERP_ENDPOINT = require_env("TALORDATA_SERP_ENDPOINT")
def call_serp_api(payload):
headers = {
"Authorization": f"Bearer {TALORDATA_API_KEY}",
"Content-Type": "application/json"
}
response = requests.post(
TALORDATA_SERP_ENDPOINT,
json=payload,
headers=headers,
timeout=30
)
response.raise_for_status()
return response.json()
def fetch_autocomplete(seed_keyword, location="United States", language="en"):
payload = {
"engine": "google_autocomplete",
"q": seed_keyword,
"location": location,
"hl": language,
"output": "json"
}
return call_serp_api(payload)
def fetch_google_search(query, location="United States", language="en", country="us"):
payload = {
"engine": "google",
"q": query,
"location": location,
"hl": language,
"gl": country,
"num": 10,
"output": "json"
}
return call_serp_api(payload)
def clean_text(value):
if not value:
return ""
return " ".join(str(value).split())
def extract_autocomplete_keywords(response_json):
raw_items = (
response_json.get("suggestions")
or response_json.get("autocomplete_results")
or response_json.get("completion_results")
or []
)
keywords = []
for item in raw_items:
if isinstance(item, str):
keywords.append(item)
elif isinstance(item, dict):
keyword = item.get("value") or item.get("suggestion") or item.get("keyword")
if keyword:
keywords.append(keyword)
return keywords
def extract_paa_questions(response_json):
raw_items = (
response_json.get("related_questions")
or response_json.get("people_also_ask")
or response_json.get("paa_results")
or []
)
questions = []
for item in raw_items:
if isinstance(item, str):
questions.append(item)
elif isinstance(item, dict):
question = item.get("question") or item.get("title")
if question:
questions.append(question)
return questions
def classify_intent(keyword):
text = keyword.lower()
if any(word in text for word in ["what", "why", "how", "guide", "tutorial"]):
return "informational"
if any(word in text for word in ["best", "top", "vs", "alternative", "compare"]):
return "commercial"
if any(word in text for word in ["price", "pricing", "cost", "free trial"]):
return "commercial"
if any(word in text for word in ["api", "python", "docs", "integration", "example"]):
return "technical"
if any(word in text for word in ["near me", "local", "map", "maps"]):
return "local"
return "general"
def suggest_content_angle(keyword, source):
intent = classify_intent(keyword)
if source == "paa":
return "FAQ section or explainer paragraph"
if intent == "technical":
return "Developer tutorial"
if intent == "commercial":
return "Comparison or buying guide"
if intent == "local":
return "Local SEO landing page or local report"
if intent == "informational":
return "Educational blog post"
return "Topic cluster supporting page"
def build_rows(seed_keyword, keywords, source):
collected_at = datetime.now(timezone.utc).isoformat()
rows = []
for keyword in keywords:
cleaned = clean_text(keyword)
if not cleaned:
continue
rows.append({
"seed_keyword": seed_keyword,
"keyword": cleaned,
"source": source,
"intent": classify_intent(cleaned),
"word_count": len(cleaned.split()),
"content_angle": suggest_content_angle(cleaned, source),
"collected_at": collected_at
})
return rows
def dedupe_rows(rows):
seen = set()
unique_rows = []
for row in rows:
key = row["keyword"].lower()
if key in seen:
continue
seen.add(key)
unique_rows.append(row)
return unique_rows
def export_to_csv(rows, filename="keyword_research_results.csv"):
if not rows:
print("No keyword ideas found.")
return
with open(filename, mode="w", newline="", encoding="utf-8") as file:
writer = csv.DictWriter(file, fieldnames=CSV_COLUMNS)
writer.writeheader()
writer.writerows(rows)
print(f"Exported {len(rows)} keyword ideas to {filename}")
if __name__ == "__main__":
seed_keyword = "serp api"
location = "United States"
autocomplete_json = fetch_autocomplete(seed_keyword, location=location)
autocomplete_keywords = extract_autocomplete_keywords(autocomplete_json)
search_json = fetch_google_search(seed_keyword, location=location)
paa_questions = extract_paa_questions(search_json)
rows = []
rows.extend(build_rows(seed_keyword, autocomplete_keywords, "autocomplete"))
rows.extend(build_rows(seed_keyword, paa_questions, "paa"))
rows = dedupe_rows(rows)
export_to_csv(rows)
After running the script, you should get:
keyword_research_results.csv
Example Output
seed_keyword,keyword,source,intent,word_count,content_angle,collected_at
serp api,serp api pricing,autocomplete,commercial,3,Comparison or buying guide,2026-06-22T00:00:00Z
serp api,serp api python,autocomplete,technical,3,Developer tutorial,2026-06-22T00:00:00Z
serp api,What is a SERP API?,paa,informational,5,FAQ section or explainer paragraph,2026-06-22T00:00:00Z
serp api,How do SERP APIs work?,paa,informational,5,FAQ section or explainer paragraph,2026-06-22T00:00:00Z
From here, you can send the CSV to Google Sheets, Airtable, Notion, a database, or an AI content planning workflow.
How to Use the Output for SEO Planning
For SEO planning, group keywords by intent:
|
Intent |
Best content format |
|
Informational |
Blog posts, explainers, guides |
|
Commercial |
Comparison pages, alternative pages, buying guides |
|
Technical |
Developer tutorials, API docs, integration guides |
|
Local |
Local SEO landing pages, location reports |
|
PAA questions |
FAQ sections, H2 sections, content brief questions |
For example, the output can become a content brief:
Topic: SERP API
Main angle: Developer tutorial
Supporting questions:
- What is a SERP API?
- How do SERP APIs work?
- Can I use a SERP API with Python?
Suggested sections:
- What the API returns
- Query parameters
- Python example
- CSV export
- FAQ
If you use Talordata SERP API for the workflow, you can extend the same structure to regular Google results, People Also Ask questions, autocomplete suggestions, related searches, and other search-result modules, depending on the data returned by your chosen endpoint. Talordata positions SERP API use cases around SEO monitoring, market research, ad verification, competitive intelligence, and AI workflows. Claim 1,000 free API responses >>
Best Practices
Save raw API responses during development. Autocomplete and PAA response structures can vary by query, location, and provider.
Keep the request layer separate from parsing. This makes it easier to change API endpoints later.
Do not rely only on autocomplete. It gives keyword variations, but not enough context by itself.
Do not rely only on People Also Ask. It gives useful questions, but it does not replace full SERP analysis.
Track location and language. Suggestions and PAA questions can change by country, city, and language.
Add search volume later. Autocomplete and PAA are good for discovery; search volume and ranking difficulty are separate metrics.
FAQ
What is the difference between autocomplete and People Also Ask?
Autocomplete shows keyword suggestions related to what users may type. People Also Ask shows question-style results related to what users may want to understand.
Can I build a keyword research tool with Python?
Yes. You can use Python to collect autocomplete suggestions, People Also Ask questions, normalize the results, classify intent, and export keyword ideas to CSV.
What is PAA data?
PAA stands for People Also Ask. It refers to question-style results that appear on Google for many searches. These questions are useful for FAQ sections, content briefs, and search intent analysis.
Is autocomplete data enough for keyword research?
No. Autocomplete is useful for discovering keyword variations, but it should be combined with SERP data, People Also Ask questions, search volume, and competitor analysis.
Can this workflow be used for content briefs?
Yes. You can group autocomplete keywords and PAA questions by intent, then turn them into article outlines, FAQ sections, comparison pages, or developer tutorials.