Extracting all keys from a JSON object is one of the most common tasks when exploring unfamiliar API responses, building data transformation pipelines, or documenting schemas. This guide covers six different methods - from instant online tools to custom code implementations in JavaScript, Python, Ruby, and the command-line tool jq.
Why You Need to Extract JSON Keys
Before writing code to process a JSON response, you need a map of what fields are available. Key extraction tells you the full structure of a JSON document, including deeply nested fields that you might miss by reading the raw JSON. It is especially valuable when:
- Integrating a new third-party API for the first time and wanting to understand its full response shape
- Building field mappings for data transformations, ETL pipelines, or database imports
- Documenting a JSON schema for your team so everyone knows what fields exist
- Debugging why a parser cannot find a field - extracting keys confirms whether the field actually exists in the response
- Comparing two API responses to find what changed between versions
- Generating code (e.g. TypeScript interfaces or Python dataclasses) based on a JSON structure
Method 1: JSON Keyper - Instant, No Code
For quick one-off exploration, JSON Keyper is the fastest approach. Paste your JSON and click Extract Keys - no code, no terminal, no dependencies:
- Copy your JSON from your API client (Postman, Insomnia, browser DevTools, etc.)
- Paste it into the left input box on JSON Keyper
- Click Extract Keys
- Every key path appears in the right box -
user.address.city,items[0].name, etc. - Click Copy to copy all paths to your clipboard
This handles nested objects and arrays automatically, outputting paths in dot notation with bracket notation for array indices.
Two options are worth knowing about, because they turn the raw path dump into something more directly usable. Collapse array indices merges items[0].sku and items[1].sku into a single items[].sku, which is what you want when documenting a schema rather than inspecting one record. And the format selector switches the same extracted structure into value-annotated paths, JSONPath expressions, an indented tree, or a generated TypeScript interface - saving you from writing the code in the sections below at all, for the common cases.
Method 2: JavaScript - Object.keys()
Object.keys() returns only the top-level keys of an object. It is useful for flat JSON but misses nested fields:
const data = {
"name": "Alice",
"age": 30,
"address": { "city": "London", "zip": "EC1A 1BB" },
"tags": ["developer", "admin"]
};
console.log(Object.keys(data));
// ["name", "age", "address", "tags"]
// NOTE: does NOT include "address.city" or "address.zip"
Method 3: Recursive JavaScript
To extract every nested key path including arrays, you need a recursive function:
function getAllKeys(obj, prefix = '') {
let keys = [];
for (const key in obj) {
if (!Object.prototype.hasOwnProperty.call(obj, key)) continue;
const fullKey = prefix ? `${prefix}.${key}` : key;
keys.push(fullKey);
const value = obj[key];
if (Array.isArray(value)) {
value.forEach((item, index) => {
if (item !== null && typeof item === 'object') {
keys = keys.concat(getAllKeys(item, `${fullKey}[${index}]`));
} else {
keys.push(`${fullKey}[${index}]`);
}
});
} else if (value !== null && typeof value === 'object') {
keys = keys.concat(getAllKeys(value, fullKey));
}
}
return keys;
}
const json = JSON.parse(jsonString);
const keys = getAllKeys(json);
console.log(keys.join('\n'));
For the example above, this would output:
name
age
address
address.city
address.zip
tags
tags[0]
tags[1]
Method 4: Python
Python's approach is clean and readable using a recursive function with generator-style logic:
import json
def get_all_keys(obj, prefix=''):
keys = []
if isinstance(obj, dict):
for k, v in obj.items():
full_key = f"{prefix}.{k}" if prefix else k
keys.append(full_key)
keys.extend(get_all_keys(v, full_key))
elif isinstance(obj, list):
for i, v in enumerate(obj):
indexed_key = f"{prefix}[{i}]"
keys.append(indexed_key)
keys.extend(get_all_keys(v, indexed_key))
return keys
# From a string
data = json.loads(json_string)
print('\n'.join(get_all_keys(data)))
# From a file
with open('response.json') as f:
data = json.load(f)
print('\n'.join(get_all_keys(data)))
Method 5: Ruby
require 'json'
def get_all_keys(obj, prefix = '')
keys = []
case obj
when Hash
obj.each do |k, v|
full_key = prefix.empty? ? k.to_s : "#{prefix}.#{k}"
keys << full_key
keys.concat(get_all_keys(v, full_key))
end
when Array
obj.each_with_index do |v, i|
indexed_key = "#{prefix}[#{i}]"
keys << indexed_key
keys.concat(get_all_keys(v, indexed_key))
end
end
keys
end
data = JSON.parse(File.read('response.json'))
puts get_all_keys(data).join("\n")
Method 6: jq - Command Line
jq is a powerful command-line JSON processor available on Linux, macOS, and Windows. It can extract all keys from a JSON file in a single command:
# Get all top-level keys
jq 'keys' data.json
# Recursively get all paths (as arrays)
jq '[path(..)] | map(join("."))' data.json
# Get all string keys (excluding array indices)
jq '[paths | select(type == "string")]' data.json
# Extract specific nested value using a path
jq '.user.address.city' data.json
# Extract all values matching a pattern
jq '.. | .name? // empty' data.json
jq is particularly useful in CI/CD pipelines, shell scripts, and when working with large JSON files where loading everything into memory is impractical.
Handling Edge Cases
When extracting keys, be aware of these common edge cases:
- Empty objects -
{}has no keys to extract - Null values - the key exists but the value is
null; still include the key path - Keys with dots - if a key name contains a literal dot (e.g.
"user.name"), dot-notation paths become ambiguous - Numeric string keys - JSON object keys must be strings, but keys like
"0"and"1"can look like array indices - Very large JSON - recursive functions can hit stack limits on extremely deep or large structures; consider iterative alternatives
Which Method Should You Use?
| Scenario | Best Method |
|---|---|
| Quick one-off exploration | JSON Keyper |
| Shell scripts or CI pipelines | jq |
| Python data pipeline | Python recursive function |
| Node.js / browser application | JavaScript recursive function |
| Top-level keys only, flat JSON | Object.keys() |
| Ruby application | Ruby recursive function |
Extract JSON Keys Instantly - No Code Required
Paste any JSON into JSON Keyper and get every nested key path in one click. Free, browser-based, no login required.
Open JSON Keyper