HikerAPI — Instagram MCP
Access Instagram data via HikerAPI's read-only API through MCP tools for profiles, posts, search, hashtags, locations, stories, and more.
Get user profiles by username, ID, or URL, including about info, web profile info, and userstream data.
Fetch followers/following lists, search within them, and get suggested profiles or recommended businesses.
Retrieve user content: medias, clips/reels, reposts, tagged medias, pinned posts, highlights, and stories.
Get media/post details by ID, code, or URL; fetch comments, replies, likers, insights, oembed data, usertags, and templates.
Search Instagram for accounts, hashtags, music, reels, places, and top content.
Get hashtag objects and top/recent/clips medias.
Get location objects, location medias (recent/top/guides), and search locations by coordinates.
Get story objects by ID/URL and download story media.
Get music/audio track details by ID or canonical ID, including track streams.
All operations are read-only GET requests; core set of ~45 tools by default, or all non-deprecated endpoints with HIKERAPI_TOOLS=all.
Requires a HikerAPI key; 100 free requests available via signup.
Provides tools to interact with Instagram data via HikerAPI, enabling retrieval of user profiles, posts, hashtags, stories, locations, comments, and more.
hikerapi-mcp
MCP server for HikerAPI — Instagram data API. Available on npm: hikerapi-mcp.
Generates MCP tools from the HikerAPI OpenAPI spec at startup. HikerAPI only exposes read (GET) endpoints — each tool maps 1:1 to one of them (GET /v2/user/by/username → get_v2_user_by_username). By default you get a core set of ~45 tools, one per task, each with a description that tells the assistant when to use it; HIKERAPI_TOOLS=all exposes every non-deprecated endpoint (100+).
Get 100 Free API Requests
Sign up with this link and get 100 free HikerAPI requests — no credit card required. Enough to wire up the MCP server, try a few prompts in Claude/Cursor/Codex, and evaluate the data quality before committing.
Related MCP server: DataLikers — Instagram & TikTok MCP
Quick start
Get an API key at hikerapi.com/tokens.
Add the server to your AI assistant.
Ask your assistant something like:
"Get the Instagram profile for @nasa."
"Find the top 5 recent posts under the hashtag
#photography.""Show stories for the user with id 25025320."
Claude Code
claude mcp add hikerapi -e HIKERAPI_KEY=your-api-key -- npx -y hikerapi-mcpClaude Desktop
Add to claude_desktop_config.json:
{
"mcpServers": {
"hikerapi": {
"command": "npx",
"args": ["-y", "hikerapi-mcp"],
"env": {
"HIKERAPI_KEY": "your-api-key"
}
}
}
}Cursor / Windsurf
Same shape as Claude Desktop — put the block under mcpServers in the app's MCP config file.
Zed
Add to ~/.config/zed/settings.json:
{
"context_servers": {
"hikerapi": {
"command": "npx",
"args": ["-y", "hikerapi-mcp"],
"env": {
"HIKERAPI_KEY": "your-api-key"
}
}
}
}OpenAI Codex
Append to ~/.codex/config.toml:
[mcp_servers.hikerapi]
command = "npx"
args = ["-y", "hikerapi-mcp"]
[mcp_servers.hikerapi.env]
HIKERAPI_KEY = "your-api-key"Tools
Tools are generated at startup from the live HikerAPI OpenAPI spec.
HikerAPI has 100+ GET endpoints, and most of them are version variants of the same call (v1 / v2 / gql / g2). Handing all of them to an assistant makes it pick the wrong one, so the default core set keeps one endpoint per task:
Group | Tools | Examples |
Profiles | 16 |
|
Posts, comments, likers | 8 |
|
Search | 7 |
|
Hashtags | 4 |
|
Locations | 3 |
|
Stories, highlights, links | 5 |
|
Audio | 1 |
|
Core tools carry hand-written descriptions (what the tool does, when to prefer a sibling, pagination, billing) and every tool is annotated read-only. The list lives in src/curated.ts.
Set HIKERAPI_TOOLS=all to expose every non-deprecated endpoint instead — same tool names as before, so existing prompts keep working. Tool names mirror their endpoint (GET /v2/user/by/username → get_v2_user_by_username); call tools/list over MCP for the current list with parameter schemas. Legacy and System groups are excluded in both modes.
Configuration
Variable | Description | Required |
| Your HikerAPI access key (sent as | yes |
| Base URL. Default: | no |
| OpenAPI spec URL. Default: | no |
|
| no |
| Whitelist: only include operations with these tags (comma-separated) | no |
| Blacklist: additional tags to exclude (on top of default | no |
| Per-request timeout for API calls. Default: | no |
| Timeout for the startup spec fetch. Default: | no |
| Base delay between the 3 startup spec fetch attempts. Default: | no |
| Max bytes read from each API response. Default: | no |
| Max bytes read from the OpenAPI spec. Default: | no |
Legacy and System tags are excluded by default. Deprecated operations are also skipped.
If HIKERAPI_URL points to a host other than api.hikerapi.com or api.instagrapi.com, the server prints a warning on startup — your key will be sent there, so only use it for a self-hosted or proxied HikerAPI.
Requests are sent with User-Agent: hikerapi-mcp/<version>.
Example — expose every endpoint of the most common groups:
"env": {
"HIKERAPI_KEY": "...",
"HIKERAPI_TOOLS": "all",
"HIKERAPI_TAGS": "User Profile,Post Details,Search,Hashtags,Stories"
}How it works
AI Assistant ←stdio→ hikerapi-mcp ──https──> api.hikerapi.com
│
└─ fetches /openapi.json once on startup,
builds one MCP tool per GET endpoint
(core set by default)Tool arguments map to the endpoint's query and path parameters. The response body is returned as-is (JSON text). Non-2xx responses are surfaced as tool errors with the HTTP status and body.
Development
git clone https://github.com/subzeroid/hikerapi-mcp.git
cd hikerapi-mcp
npm install
npm run build
HIKERAPI_KEY=your-key node dist/index.jsRun in watch mode:
HIKERAPI_KEY=your-key npm run devRun tests (unit + stdio smoke tests against a local mock server, no network/API key required):
npm testLicense
MIT
Available Tools
44 toolsget_g2_location_by_idARead-only
Get an Instagram location by id: name, latitude/longitude, category and description. Use get_v1_fbsearch_places or get_v1_location_search to find the id first, and the location media tools for posts made there. Live request to Instagram, billed per call. (GET /g2/location/by/id)
Inputs: id (required).
get_g2_user_followersARead-only
List accounts that follow an Instagram user, one page per call. Use it to page through the follower list; use get_v1_user_search_followers to look for specific names among them and get_g2_user_following for accounts the user follows. Pass user_id; for the next page pass the cursor from the previous response as page_id. Live request to Instagram, one billed request per page. (GET /g2/user/followers)
Inputs: user_id (required), page_id.
get_g2_user_followingARead-only
List accounts an Instagram user follows, one page per call. Use it to page through the following list; use get_v1_user_search_following to look for specific names in it and get_g2_user_followers for the user's followers. Pass user_id; for the next page pass the cursor from the previous response as page_id. Live request to Instagram, one billed request per page. (GET /g2/user/following)
Inputs: user_id (required), page_id.
get_gql_comment_likers_chunkARead-only
Get users who liked one comment on an Instagram post, one page per call. Pass comment_id and media_id; paginate with end_cursor from the previous response. Use get_v2_media_likers for likers of the post itself. Live request to Instagram, billed per call. (GET /gql/comment/likers/chunk)
Inputs: media_id, comment_id, end_cursor.
get_gql_media_usertagsARead-only
Get the users tagged in Instagram videos; pass up to 10 media ids in media_ids. Use it for reels and videos, because the get_v2_media_info_* tools do not return user tags for video. Live request to Instagram, billed per call. (GET /gql/media/usertags)
Inputs: media_ids.
get_gql_user_aboutARead-only
Get the "About this account" panel for an Instagram user id: verified status, country of registration, account creation date and former usernames. Use it for account provenance checks; use get_v2_user_by_id for the regular profile. Live request to Instagram, billed per call. (GET /gql/user/about)
Inputs: id (required).
get_gql_user_mediasARead-only
List an Instagram user's posts, one page per call. Use it to read an account's feed; use get_v2_user_clips for reels only and get_v2_user_tag_medias for posts the user is tagged in. Pass user_id; for the next page pass the cursor from the previous response as profile_grid_items_cursor. flat=true flattens nested media objects into a single list. Live request to Instagram, billed per call. (GET /gql/user/medias)
Inputs: user_id (required), flat, profile_grid_items_cursor.
get_gql_user_repostsARead-only
List content an Instagram user has reposted, one page per call. Use get_gql_user_medias for the user's own posts. Pass user_id; for the next page pass the cursor from the previous response as repost_next_max_id. flat=true returns a simple items list. Live request to Instagram, billed per call. (GET /gql/user/reposts)
Inputs: user_id (required), flat, repost_next_max_id.
get_v1_fbsearch_placesARead-only
Search Instagram places by name (query), optionally with lat and lng. Use it to find a location id for get_g2_location_by_id and the location media tools; use get_v1_location_search when you only have coordinates. Live request to Instagram, billed per call. (GET /v1/fbsearch/places)
Inputs: query (required), lat, lng.
get_v1_hashtag_by_nameARead-only
Get an Instagram hashtag by exact name (no # and no special characters). Use it for the hashtag's own info; use get_v2_hashtag_medias_top or get_v2_hashtag_medias_recent for its posts and get_v1_search_hashtags when unsure of the exact tag. Live request to Instagram, billed per call. (GET /v1/hashtag/by/name)
Inputs: name (required).
get_v1_hashtag_medias_clips_chunkARead-only
List reels under an Instagram hashtag, one page per call. Use get_v2_hashtag_medias_top or get_v2_hashtag_medias_recent for all post types and get_v2_fbsearch_reels to search reels by free text. Pass name without #; paginate with max_id from the previous response. Live request to Instagram, billed per call. (GET /v1/hashtag/medias/clips/chunk)
Inputs: name (required), max_id.
get_v1_highlight_by_urlARead-only
Get one Instagram story highlight by its link. For share links that contain /s/, call get_v1_share_by_url first to resolve them. Use get_v2_highlight_by_id when you have the id. Live request to Instagram, billed per call. (GET /v1/highlight/by/url)
Inputs: url (required).
get_v1_location_medias_recent_chunkARead-only
List recent posts made at an Instagram location, one page per call. Pass location_pk; paginate with max_id from the previous response. Use get_v1_location_medias_top_chunk for top posts. Live request to Instagram, billed per call. (GET /v1/location/medias/recent/chunk)
Inputs: location_pk (required), max_id.
get_v1_location_medias_top_chunkARead-only
List top posts made at an Instagram location, one page per call. Pass location_pk; paginate with max_id from the previous response. Use get_v1_location_medias_recent_chunk for the newest posts. Live request to Instagram, billed per call. (GET /v1/location/medias/top/chunk)
Inputs: location_pk (required), max_id.
get_v1_location_searchARead-only
Find Instagram locations at a coordinate: pass lat and lng. Use get_v1_fbsearch_places to search places by name instead. Live request to Instagram, billed per call. (GET /v1/location/search)
Inputs: lat (required), lng (required).
get_v1_search_hashtagsARead-only
Search Instagram hashtags by keyword. Use it when unsure of the exact tag; use get_v1_hashtag_by_name for one known hashtag. Live request to Instagram, billed per call. (GET /v1/search/hashtags)
Inputs: query (required).
get_v1_search_musicARead-only
Search Instagram music tracks by keyword (song or artist). Use get_v2_track_by_id for one known track. Live request to Instagram, billed per call. (GET /v1/search/music)
Inputs: query (required).
get_v1_user_search_followersARead-only
Search within an Instagram user's followers by name or username. Use it to check whether specific accounts follow a user; use get_g2_user_followers to list all followers. Pass user_id and query; force=true skips the account privacy check. Live request to Instagram, billed per call. (GET /v1/user/search/followers)
Inputs: query (required), user_id (required), force.
get_v1_user_search_followingARead-only
Search within the accounts an Instagram user follows by name or username. Use it to check whether a user follows specific accounts; use get_g2_user_following to list all of them. Pass user_id and query; force=true skips the account privacy check. Live request to Instagram, billed per call. (GET /v1/user/search/following)
Inputs: query (required), user_id (required), force.
get_v2_fbsearch_accountsARead-only
Search Instagram accounts by keyword. Use it to find a profile when you do not know the exact handle; use get_v2_user_by_username for an exact handle. Paginate with page_token from the previous response. Live request to Instagram, billed per call. (GET /v2/fbsearch/accounts)
Inputs: query (required), safe_int, page_token.
get_v2_fbsearch_reelsARead-only
Search Instagram reels by keyword. Use it to find short videos about a topic; use get_v1_hashtag_medias_clips_chunk for reels under one specific hashtag. Paginate with reels_max_id and rank_token from the previous response. Live request to Instagram, billed per call. (GET /v2/fbsearch/reels)
Inputs: query (required), safe_int, rank_token, reels_max_id.
get_v2_fbsearch_topsearchARead-only
Search Instagram for top content by keyword. Use it for a broad first look; use get_v2_fbsearch_accounts to search only accounts, get_v2_fbsearch_reels only reels and get_v1_search_hashtags only hashtags. Paginate with next_max_id from the previous response. Live request to Instagram, billed per call. (GET /v2/fbsearch/topsearch)
Inputs: query (required), safe_int, next_max_id.
get_v2_hashtag_medias_recentARead-only
List recent posts under an Instagram hashtag, one page per call. Use get_v2_hashtag_medias_top for top posts and get_v1_hashtag_medias_clips_chunk for reels only. Pass name without #; for the next page pass next_page_id from the previous response as page_id. Live request to Instagram, billed per call. (GET /v2/hashtag/medias/recent)
Inputs: name (required), page_id, safe_int.
get_v2_hashtag_medias_topARead-only
List top posts under an Instagram hashtag, one page per call. Use get_v2_hashtag_medias_recent for the newest posts and get_v1_hashtag_medias_clips_chunk for reels only. Pass name without #; for the next page pass next_page_id from the previous response as page_id. Live request to Instagram, billed per call. (GET /v2/hashtag/medias/top)
Inputs: name (required), page_id, safe_int.
get_v2_highlight_by_idARead-only
Get one Instagram story highlight by id. Use get_v2_user_highlights to list a user's highlights and get_v1_highlight_by_url when you have a link. Live request to Instagram, billed per call. (GET /v2/highlight/by/id)
Inputs: id (required), safe_int.
get_v2_media_commentsARead-only
Get comments on an Instagram post, about 15 per call. Pass the media id; for the next page pass the page id from the previous response as page_id. Use get_v2_media_comments_replies for replies under one comment and get_v2_media_likers for users who liked the post. Live request to Instagram, one billed request per page. (GET /v2/media/comments)
Inputs: id (required), page_id, safe_int, can_support_threading.
get_v2_media_comments_repliesARead-only
Get replies under one comment of an Instagram post. Use it to read a thread; use get_v2_media_comments for the top-level comments. Pass media_id and comment_id (both from the comments tool); paginate with min_id from the previous response. Live request to Instagram, billed per call. (GET /v2/media/comments/replies)
Inputs: media_id (required), comment_id (required), min_id, safe_int.
get_v2_media_info_by_codeARead-only
Get an Instagram post or reel by its shortcode (the part after /p/ or /reel/ in the link). Use get_v2_media_info_by_url when you have a full link and get_v2_media_info_by_id for a numeric media id. Returns the media object, or 404 for deleted or unavailable posts; promoted (ad) posts may also return 404. User tags are not included for videos, use get_gql_media_usertags for those. Live request to Instagram, billed per call. (GET /v2/media/info/by/code)
Inputs: code (required), safe_int.
get_v2_media_info_by_idARead-only
Get an Instagram post or reel by numeric media id. Use get_v2_media_info_by_code for a shortcode and get_v2_media_info_by_url for a full link. Returns the media object, or 404 for deleted or unavailable posts; promoted (ad) posts may also return 404. User tags are not included for videos, use get_gql_media_usertags for those. Live request to Instagram, billed per call. (GET /v2/media/info/by/id)
Inputs: id (required), safe_int.
get_v2_media_info_by_urlARead-only
Get an Instagram post or reel by its link (instagram.com/p/... or /reel/...). Use get_v2_media_info_by_code for a bare shortcode. Returns the media object, 404 for deleted or unavailable posts and 400 for links that are not posts: use get_v2_story_by_url for story links and get_v1_share_by_url for /s/ share links. Promoted (ad) posts may also return 404. Live request to Instagram, billed per call. (GET /v2/media/info/by/url)
Inputs: url (required), safe_int.
get_v2_media_likersARead-only
Get users who liked an Instagram post, by media id. Use get_gql_comment_likers_chunk for likers of a single comment and get_v2_media_comments for commenters. Live request to Instagram, billed per call. (GET /v2/media/likers)
Inputs: id (required), safe_int.
get_v2_story_by_idARead-only
Get one Instagram story by its id. Use get_v2_story_by_url when you have a story link and get_v2_user_stories to list a user's active stories. Live request to Instagram, billed per call. (GET /v2/story/by/id)
Inputs: id (required), safe_int.
get_v2_story_by_urlARead-only
Get one Instagram story by its link. For share links that contain /s/, call get_v1_share_by_url first to resolve them. Use get_v2_story_by_id when you have the id. Live request to Instagram, billed per call. (GET /v2/story/by/url)
Inputs: url (required), safe_int.
get_v2_track_by_idARead-only
Get an Instagram music track by track_id. Use get_v1_search_music to find tracks by keyword. For the next page pass next_page_id from the previous response as page_id. Live request to Instagram, billed per call. (GET /v2/track/by/id)
Inputs: track_id (required), page_id, safe_int.
get_v2_user_by_idARead-only
Get an Instagram profile by numeric user id. Use it when you already have the id from another tool; use get_v2_user_by_username when you only have a handle. Returns the same user object. Live request to Instagram, billed per call. (GET /v2/user/by/id)
Inputs: id (required), safe_int.
get_v2_user_by_usernameARead-only
Get an Instagram profile by username (without @). Use it when you have a handle; use get_v2_user_by_id when you already know the numeric user id (faster), and get_gql_user_about for the "About this account" panel. Returns the user object; pass its pk as the user id to the other user tools. Live request to Instagram, one billed request per call. (GET /v2/user/by/username)
Inputs: username (required), safe_int.
get_v2_user_clipsARead-only
List an Instagram user's reels (short videos), one page per call. Use it for reels only; use get_gql_user_medias for all posts. Pass user_id; for the next page pass next_page_id from the previous response as page_id. Live request to Instagram, billed per call. (GET /v2/user/clips)
Inputs: page_id, user_id, safe_int.
get_v2_user_highlightsARead-only
List an Instagram user's story highlights (saved story collections) by user id, one page per call. Use get_v2_highlight_by_id to open one highlight and get_v2_user_highlights_by_username when you only have a handle. For the next page pass next_page_id from the previous response as page_id (amount is ignored). Live request to Instagram, billed as 2 requests per call. (GET /v2/user/highlights)
Inputs: user_id (required), force, amount, page_id, +1 more.
get_v2_user_highlights_by_usernameARead-only
List an Instagram user's story highlights by username, one page per call. Use it only when you have a handle and not the user id: it is slower than get_v2_user_highlights and billed as 3 requests per call instead of 2. For the next page pass next_page_id from the previous response as page_id. Live request to Instagram. (GET /v2/user/highlights/by/username)
Inputs: username (required), force, amount, page_id, +1 more.
get_v2_user_storiesARead-only
Get an Instagram user's active stories by user id. Use it when you have the id; use get_v2_user_stories_by_username when you only have a handle and get_v2_user_highlights for saved highlight collections. force=true skips the account privacy check. Live request to Instagram, billed as 2 requests per call. (GET /v2/user/stories)
Inputs: user_id (required), force, safe_int.
get_v2_user_stories_by_usernameARead-only
Get an Instagram user's active stories by username. Use it only when you have a handle and not the user id: it is slower than get_v2_user_stories and billed as 3 requests per call instead of 2. Live request to Instagram. (GET /v2/user/stories/by/username)
Inputs: username (required), force, safe_int.
get_v2_user_suggested_profilesARead-only
Get the accounts Instagram suggests as related to a given user. Use it to find similar accounts; use get_v2_fbsearch_accounts to search accounts by keyword instead. Pass user_id; expand_suggestion=true returns more detail per account. Live request to Instagram, billed per call. (GET /v2/user/suggested/profiles)
Inputs: user_id (required), safe_int, expand_suggestion.
get_v2_user_tag_mediasARead-only
List posts in which an Instagram user is tagged, one page per call. Use it to see who features an account; use get_gql_user_medias for the user's own posts. Pass user_id; for the next page pass next_page_id from the previous response as page_id. Live request to Instagram, billed per call. (GET /v2/user/tag/medias)
Inputs: page_id, user_id, safe_int.
Tool Schema Changelog
Recent tool additions, removals, and schema changes observed during successful MCP inspections.
Loading tool schema changelog…
TDQS
Scored across 44 tools
The tools cover many distinct Instagram resources and actions, and descriptions explicitly cross-reference alternatives such as by id vs username vs URL vs shortcode, or top vs recent vs clips. While no two tools are truly interchangeable, the sheer number of near-variants increases cognitive load and misselection risk.
All tools use a get_ + lowercase snake_case convention, making the pattern predictable. Minor inconsistency comes from mixed API-version prefixes (v1, v2, gql, g2) and compound tokens like fbsearch, usertags, and clips_chunk, but the naming remains readable and largely consistent.
44 tools far exceeds the typical 3-15 range and includes many access-method variants that could be consolidated into fewer flexible tools. While each maps to a real endpoint, the set is heavy and likely to overwhelm tool selection.
The surface covers users, media, comments, likes, stories, highlights, search, hashtags, locations, music, followers/following, suggestions, and account provenance, giving broad read-only Instagram coverage. Gaps exist for less common data such as live videos, saved media, or media by music track, but core workflows are covered.
Maintenance
Related MCP Connectors
Hosted MCP server for DataLikers — Instagram & TikTok data API. 51 tools: Instagram user search by demographics (gender/age/race/country/city), profiles, bulk lookup, engagement, posts & reels, comments, hashtags, locations, stories, highlights, music, business accounts, top users; TikTok users, videos, comments, hashtags, playlists and top charts. Streamable HTTP, Bearer API key. Free tier: 100 requests on signup at https://datalikers.com/p/1by27bwg
Instagram data over MCP: profiles, posts, reels, stories, highlights and search as JSON
Unified social scraper MCP — profiles, posts, videos across ~40 platforms via Streamable HTTP.
Hosted Instagram MCP server for Claude, ChatGPT and Cursor, with each action switched per account.
Related MCP Servers
- AlicenseAqualityBmaintenanceMCP server for LamaTok TikTok data API — auto-generates 20+ tools from the live OpenAPI spec (users, videos, hashtags, music, comments). Local stdio via npx -y lamatok-mcp, requires only LAMATOK_KEY.2361 npm1MIT
- AlicenseNot gradedqualityCmaintenanceMCP server for DataLikers — 51 tools for Instagram & TikTok data: Instagram user search by demographics (gender/age/race/country/city), profiles, engagement, posts, comments, hashtags, locations, stories, business accounts; TikTok users, videos, comments, hashtags, playlists. Local stdio via npx -y datalikers-mcp, requires only DATALIKERS_API_KEY.64 npm9MIT
- AlicenseAqualityCmaintenance16 Instagram creator tools as an MCP server — Reels/Story/carousel downloaders, engagement audit, hashtag search, Reels hook generator, best-time-to-post and content calendar. Wraps instapdown.com public API — no auth required.1656 npm2MIT
- AlicenseNot gradedqualityCmaintenanceMCP server for downloading Instagram content (videos, reels, audio, carousels) using yt-dlp, with tools for downloading media and fetching metadata. Supports stdio and HTTP transports.MIT