MCPInstall

airtable

Airtable REST API via curl. Records CRUD, filters, upserts.

Installs
376
Last 24h
—
Trending rank
—
Security
Not audited

Install

Works with every agent the skills CLI supports.

npx skills add https://github.com/nousresearch/hermes-agent --skill airtable
  1. 01

    Install

    Run the command in your project. The CLI asks which agents to install for.

  2. 02

    Describe the task

    Ask your agent for something this skill covers. It loads airtable automatically when relevant.

  3. 03

    Review the result

    The agent follows the SKILL.md steps, scripts and references bundled with the skill.

SKILL.md

The instructions your agent reads when the skill is triggered.

Airtable — Bases, Tables & Records

Work with Airtable's REST API directly via curl using the terminal tool. No MCP server, no OAuth flow, no Python SDK — just curl and a personal access token.

Prerequisites

  1. Create a Personal Access Token (PAT) at https://airtable.com/create/tokens (tokens start with pat...).
  2. Grant these scopes (minimum):
    • data.records:read — read rows
    • data.records:write — create / update / delete rows
    • schema.bases:read — list bases and tables
  3. Important: in the same token UI, add each base you want to access to the token's Access list. PATs are scoped per-base — a valid token on the wrong base returns 403.
  4. Store the token in ${HERMES_HOME:-~/.hermes}/.env (or via hermes setup):
    AIRTABLE_API_KEY=pat_your_token_here
    

Note: legacy key... API keys were deprecated Feb 2024. Only PATs and OAuth tokens work now.

API Basics

  • Endpoint: https://api.airtable.com/v0
  • Auth header: Authorization: Bearer $AIRTABLE_API_KEY
  • All requests use JSON (Content-Type: application/json for any POST/PATCH/PUT body).
  • Object IDs: bases app..., tables tbl..., records rec..., fields fld.... IDs never change; names can. Prefer IDs in automations.
  • Rate limit: 5 requests/sec/base. 429 → back off. Burst on a single base will be throttled.

Base curl pattern:

curl -s "https://api.airtable.com/v0/$BASE_ID/$TABLE?maxRecords=5" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

-s suppresses curl's progress bar — keep it set for every call so the tool output stays clean for Hermes. Pipe through python -m json.tool (always present) or jq (if installed) for readable JSON.

Field Types (request body shapes)

Field typeWrite shape
Single line text"Name": "hello"
Long text"Notes": "multi\nline"
Number"Score": 42
Checkbox"Done": true
Single select"Status": "Todo" (name must already exist unless typecast: true)
Multi-select"Tags": ["urgent", "bug"]
Date"Due": "2026-04-01"
DateTime (UTC)"At": "2026-04-01T14:30:00.000Z"
URL / Email / Phone"Link": "https://…"
Attachment"Files": [{"url": "https://…"}] (Airtable fetches + rehosts)
Linked record"Owner": ["recXXXXXXXXXXXXXX"] (array of record IDs)
User"AssignedTo": {"id": "usrXXXXXXXXXXXXXX"}

Pass "typecast": true at the top level of a create/update body to let Airtable auto-coerce values (e.g. create a new select option on the fly, convert "42" → 42).

Common Queries

List bases the token can see

curl -s "https://api.airtable.com/v0/meta/bases" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

List tables + schema for a base

curl -s "https://api.airtable.com/v0/meta/bases/$BASE_ID/tables" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Use this BEFORE mutating — confirms exact field names and IDs, surfaces options.choices for select fields, and shows primary-field names.

List records (first 10)

curl -s "https://api.airtable.com/v0/$BASE_ID/$TABLE?maxRecords=10" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Get a single record

curl -s "https://api.airtable.com/v0/$BASE_ID/$TABLE/$RECORD_ID" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Filter records (filterByFormula)

Airtable formulas must be URL-encoded. Let Python stdlib do it — never hand-encode:

FORMULA="{Status}='Todo'"
ENC=$(python -c 'import sys, urllib.parse; print(urllib.parse.quote(sys.argv[1], safe=""))' "$FORMULA")
curl -s "https://api.airtable.com/v0/$BASE_ID/$TABLE?filterByFormula=$ENC&maxRecords=20" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Useful formula patterns:

  • Exact match: {Email}='user@example.com'
  • Contains: FIND('bug', LOWER({Title}))
  • Multiple conditions: AND({Status}='Todo', {Priority}='High')
  • Or: OR({Owner}='alice', {Owner}='bob')
  • Not empty: NOT({Assignee}='')
  • Date comparison: IS_AFTER({Due}, TODAY())

Sort + select specific fields

curl -s "https://api.airtable.com/v0/$BASE_ID/$TABLE?sort%5B0%5D%5Bfield%5D=Priority&sort%5B0%5D%5Bdirection%5D=asc&fields%5B%5D=Name&fields%5B%5D=Status" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Square brackets in query params MUST be URL-encoded (%5B / %5D).

Use a named view

curl -s "https://api.airtable.com/v0/$BASE_ID/$TABLE?view=Grid%20view&maxRecords=50" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Views apply their saved filter + sort server-side.

Common Mutations

Create a record

curl -s -X POST "https://api.airtable.com/v0/$BASE_ID/$TABLE" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"fields":{"Name":"New task","Status":"Todo","Priority":"High"}}' | python -m json.tool

Create up to 10 records in one call

curl -s -X POST "https://api.airtable.com/v0/$BASE_ID/$TABLE" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "typecast": true,
    "records": [
      {"fields": {"Name": "Task A", "Status": "Todo"}},
      {"fields": {"Name": "Task B", "Status": "In progress"}}
    ]
  }' | python -m json.tool

Batch endpoints are capped at 10 records per request. For larger inserts, loop in batches of 10 with a short sleep to respect 5 req/sec/base.

Update a record (PATCH — merges, preserves unchanged fields)

curl -s -X PATCH "https://api.airtable.com/v0/$BASE_ID/$TABLE/$RECORD_ID" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"fields":{"Status":"Done"}}' | python -m json.tool

Upsert by a merge field (no ID needed)

curl -s -X PATCH "https://api.airtable.com/v0/$BASE_ID/$TABLE" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "performUpsert": {"fieldsToMergeOn": ["Email"]},
    "records": [
      {"fields": {"Email": "user@example.com", "Status": "Active"}}
    ]
  }' | python -m json.tool

performUpsert creates records whose merge-field values are new, patches records whose merge-field values already exist. Great for idempotent syncs.

Delete a record

curl -s -X DELETE "https://api.airtable.com/v0/$BASE_ID/$TABLE/$RECORD_ID" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Delete up to 10 records in one call

curl -s -X DELETE "https://api.airtable.com/v0/$BASE_ID/$TABLE?records%5B%5D=rec1&records%5B%5D=rec2" \
  -H "Authorization: Bearer $AIRTABLE_API_KEY" | python -m json.tool

Pagination

List endpoints return at most 100 records per page. If the response includes "offset": "...", pass it back on the next call. Loop until the field is absent:

OFFSET=""
while :; do
  URL="https://api.airtable.com/v0/$BASE_ID/$TABLE?pageSize=100"
  [ -n "$OFFSET" ] && URL="$URL&offset=$OFFSET"
  RESP=$(curl -s "$URL" -H "Authorization: Bearer $AIRTABLE_API_KEY")
  echo "$RESP" | python -c 'import json,sys; d=json.load(sys.stdin); [print(r["id"], r["fields"].get("Name","")) for r in d["records"]]'
  OFFSET=$(echo "$RESP" | python -c 'import json,sys; d=json.load(sys.stdin); print(d.get("offset",""))')
  [ -z "$OFFSET" ] && break
done

Typical Hermes Workflow

  1. Confirm auth. curl -s -o /dev/null -w "%{http_code}\n" https://api.airtable.com/v0/meta/bases -H "Authorization: Bearer $AIRTABLE_API_KEY" — expect 200.
  2. Find the base. List bases (step above) OR ask the user for the app... ID directly if the token lacks schema.bases:read.
  3. Inspect the schema. GET /v0/meta/bases/$BASE_ID/tables — cache the exact field names and primary-field name locally in the session before mutating anything.
  4. Read before you write. For "update X where Y", filterByFormula first to resolve the rec... ID, then PATCH /v0/$BASE_ID/$TABLE/$RECORD_ID. Never guess record IDs.
  5. Batch writes. Combine related creates into one 10-record POST to stay under the 5 req/sec budget.
  6. Destructive ops. Deletions can't be undone via API. If the user says "delete all Xs", echo back the filter + record count and confirm before firing.

Pitfalls

  • filterByFormula MUST be URL-encoded. Field names with spaces or non-ASCII also need encoding ({My Field} → %7BMy%20Field%7D). Use Python stdlib (pattern above) — never hand-escape.
  • Empty fields are omitted from responses. A missing "Assignee" key doesn't mean the field doesn't exist — it means this record's value is empty. Check the schema (step 3) before concluding a field is missing.
  • PATCH vs PUT. PATCH merges supplied fields into the record. PUT replaces the record entirely and clears any field you didn't include. Default to PATCH.
  • Single-select options must exist. Writing "Status": "Shipping" when Shipping isn't in the field's option list errors with INVALID_MULTIPLE_CHOICE_OPTIONS unless you pass "typecast": true (which auto-creates the option).
  • Per-base token scoping. A 403 on one base while another works means the token's Access list doesn't include that base — not a scope or auth issue. Send the user to https://airtable.com/create/tokens to grant it.
  • Rate limits are per base, not per token. 5 req/sec on baseA and 5 req/sec on baseB is fine; 6 req/sec on baseA alone will throttle. Monitor the Retry-After header on 429.

Important Notes for Hermes

  • Always use the terminal tool with curl. Do NOT use web_extract (it can't send auth headers) or browser_exec (needs UI auth and is slow).
  • AIRTABLE_API_KEY flows from ${HERMES_HOME:-~/.hermes}/.env into the subprocess automatically when this skill is loaded — no need to re-export it before each curl call.
  • Escape curly braces in formulas carefully. In a heredoc body, {Status} is literal. In a shell argument, {Status} is safe outside {...} brace-expansion context — but pass dynamic strings through python urllib.parse.quote before splicing into a URL.
  • Pretty-print with python -m json.tool (always present) rather than jq (optional). Only reach for jq when you need filtering/projection.
  • Pagination is per-page, not global. Airtable's 100-record cap is a hard limit; there is no way to bump it. Loop with offset until the field is absent.
  • Read the errors array on non-2xx responses — Airtable returns structured error codes like AUTHENTICATION_REQUIRED, INVALID_PERMISSIONS, MODEL_ID_NOT_FOUND, INVALID_MULTIPLE_CHOICE_OPTIONS that tell you exactly what's wrong.

FAQ

What does the airtable skill do?

Airtable REST API via curl. Records CRUD, filters, upserts.

How do I install airtable?

Run npx skills add https://github.com/nousresearch/hermes-agent --skill airtable in your project. The skills CLI detects the agents you use and copies the skill into the right folder. For Claude Code you can also place the skill folder at ~/.claude/skills/airtable/ (personal) or .claude/skills/airtable/ (project).

Which AI agents can use airtable?

Any agent that supports the open Agent Skills format (a folder with a SKILL.md file), including Claude Code, Codex, Cursor, GitHub Copilot, Gemini CLI, Windsurf, Cline, OpenCode and more.

Is airtable safe to install?

No partner security audit is available yet. Skills can run commands and scripts, so read the SKILL.md and any bundled files before installing.

Who maintains airtable?

It is published by nousresearch in nousresearch/hermes-agent. It has 376 recorded installs.

More from nousresearch/hermes-agent

View all →

dogfood

nousresearch/hermes-agent

Exploratory QA of web apps: find bugs, evidence, reports.

Testing & QA6.4K installs

humanizer

nousresearch/hermes-agent

Humanize text: strip AI-isms and add real voice.

Media & Creative1.3K installs

hermes-agent

nousresearch/hermes-agent

Use, configure, theme, extend, and orchestrate Hermes Agent.

Frontend & Design1.1K installs

popular-web-designs

nousresearch/hermes-agent

54 real design systems (Stripe, Linear, Vercel) as HTML/CSS.

Frontend & Design921 installs

powerpoint

nousresearch/hermes-agent

Create, read, edit .pptx decks with python-pptx.

Docs & Writing754 installs

arxiv

nousresearch/hermes-agent

Search arXiv papers by keyword, author, category, or ID.

Popular backend & apis skills

View category →

find-skills

vercel-labs/skills

Helps users discover and install agent skills when they ask questions like "how do I do X", "find a skill for X", "is there a skill that can...", or express interest in extending capabilities. This skill should be used when the user is looking for functionality that might exist as an installable skill.

OfficialBackend & APIs4.1M installs

entra-app-registration

microsoft/azure-skills

Guides Microsoft Entra ID app registration, OAuth 2.0 authentication, and MSAL integration. USE FOR: create app registration, register Azure AD app, configure OAuth, set up authentication, add API permissions, generate service principal, MSAL example, console app auth, Entra ID setup, Azure AD authentication. DO NOT USE FOR: Key Vault secrets (use azure-keyvault-expiration-audit), general Azure resource security guidance.

OfficialBackend & APIs566.7K installs

This skill should be used when the user wants to "write agent code", "build an agent with ADK", "add a tool", "create a callback", "define an agent", "use state management" — in a project that needs ADK (Agent Development Kit) API patterns and code examples. It provides a quick reference for agent types, tool definitions, orchestration patterns, callbacks, state management, the graph Workflow API, and reference recipes to study. Do NOT use for scaffolding (use google-agents-cli-scaffold) or deployment (use google-agents-cli-deploy).

Backend & APIs514.8K installs

embedded-captions

heygen-com/hyperframes

Add captions or subtitles to an existing single-subject talking-head video without editing the footage. Use for plain verbatim captions, cinematic captions embedded behind the subject, VFX captions, “炸/特效/酷炫字幕,” or a named identity from the 35-style catalog. Route by visual identity, not by backend engine. The quiet anchor rail is the default; embed every word only when the user explicitly wants a fully cinematic treatment. The workflow runs locally end to end, including transcription and subject matting; split multi-shot footage before applying it.

Backend & APIs453.3K installs

entra-agent-id

microsoft/azure-skills

Provision Microsoft Entra Agent Identity Blueprints, BlueprintPrincipals, and per-instance Agent Identities via Microsoft Graph, and configure OAuth 2.0 token exchange (fmipath, OBO, cross-tenant) including the Microsoft Entra SDK for AgentID sidecar. USE FOR: Agent Identity Blueprint, BlueprintPrincipal, agent OAuth, fmipath token exchange, agent OBO, Workload Identity Federation for agents, polyglot agent auth, Microsoft.Identity.Web.AgentIdentities. DO NOT USE FOR: standard Entra app registration (use entra-app-registration), Microsoft Foundry agent authoring (use microsoft-foundry).

OfficialBackend & APIs336.6K installs

neon

neondatabase/agent-skills

Overview of Neon, a complete set of cloud backend primitives around Lakebase Postgres: Auth, Object Storage, Functions, the AI Gateway, and Realtime. Start here to choose Neon for undecided login, files, APIs, and LLM calls, set up the CLI or MCP server, and follow the branch-first workflow. Use when building an app or backend on Neon, or when "Neon" or "Lakebase Postgres" is mentioned. Child skill neon-postgres wins for an existing DATABASEURL, SQL, schema, inspect, or search. Child skill neon-auth wins for login, users, sessions, identity routing, and Managed Better Auth setup. Child skill neon-realtime wins for live queries in reactive apps and agents. Also use for object storage, S3, buckets, serverless functions, function triggers, cron, AI gateway, LLM calls, realtime, logs, Loki, Grafana, observability, postgres, database, backend, Claimable Neon, neon.new, or a no-signup database.

Backend & APIs237.1K installs