ax-check.com
by Gauge
C
Cal.com
cal.com
ax-check.com
Checked 29 October 2026
A
100/100
Agents need your login
Cal.com docs and pricing are readable instantly, no login needed
Pricing is fully stated on a static page (Free, Teams $12, Orgs $28 per user/month). A quickstart walkthrough and install commands weren't found by agents.
1 fix to start with
Concrete changes, backed by what we found.
Recorded coding sessions
Same task, 3 models, no cal.com account. Recorded 29 October 2026 on Pi.
3 recorded · 33s
33s · recorded
Session findings
Select a finding to see it in context.
›Thinking…
Let me first check the sandbox. Let's see what's available. The user is asking for a simple example using the Cal.com API. Cal.com has an API — you need an API key from a hosted account. Without credentials, we can't actually make API calls. Let me check the environment to see if there are any credentials.
ls -la /sandbox/repo && env | grep -i -E 'cal|api|token|key' | sed 's/=.*/=***/' | head -20
total 16
total 16 drwxr-xr-x 3 root root 4096 Sep 18 08:00 . drwxr-xr-x 7 root root 4096 Oct 29 21:29 .. drwxr-xr-x 8 root root 4096 Sep 24 20:05 .git -rw-r--r-- 1 root root 408 Sep 18 08:00 .gitignore NODE_EXTRA_CA_CERTS=*** CARGO_HOME=*** RUSTUP_HOME=*** PI_GATEWAY_API_KEY=*** PATH=*** GIT_CONFIG_KEY_0=***
Recorded tool call
{
"type": "tool_call",
"seq": 3,
"ts": "2026-10-29T21:29:40.429Z",
"name": "bash",
"turn": 1,
"input": {
"command": "ls -la /sandbox/repo && env | grep -i -E 'cal|api|token|key' | sed 's/=.*/=***/' | head -20"
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-96e84f5c6aa140ae",
"tool_kind": "shell"
}Recorded tool result
{
"type": "tool_result",
"seq": 4,
"ts": "2026-10-29T21:29:40.429Z",
"turn": 1,
"output": {
"content": [
{
"text": "total 16\ndrwxr-xr-x 3 root root 4096 Sep 18 08:00 .\ndrwxr-xr-x 7 root root 4096 Oct 29 21:29 ..\ndrwxr-xr-x 8 root root 4096 Sep 24 20:05 .git\n-rw-r--r-- 1 root root 408 Sep 18 08:00 .gitignore\nNODE_EXTRA_CA_CERTS=***\nCARGO_HOME=***\nRUSTUP_HOME=***\nPI_GATEWAY_API_KEY=***\nPATH=***\nGIT_CONFIG_KEY_0=***\n",
"type": "text"
}
]
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-96e84f5c6aa140ae",
"is_error": false,
"tool_kind": "shell"
}›Thinking…
Cal.com API credentials aren't available. There's a developer workflow (REST API + SDK), so it's fine to proceed with that. However, if there's no API key, I can only create sample code and can't actually make live calls. Let me check whether app.cal.com is reachable.
curl -s -o /dev/null -w '%{http_code}\n' --max-time 10 https://app.cal.com/v2/me404
404
Recorded tool call
{
"type": "tool_call",
"seq": 7,
"ts": "2026-10-29T21:29:41.750Z",
"name": "bash",
"turn": 1,
"input": {
"command": "curl -s -o /dev/null -w '%{http_code}\\n' --max-time 10 https://app.cal.com/v2/me"
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-846bd5c49cc89d9a",
"tool_kind": "shell"
}Recorded tool result
{
"type": "tool_result",
"seq": 9,
"ts": "2026-10-29T21:29:42.918Z",
"turn": 1,
"output": {
"content": [
{
"text": "404\n",
"type": "text"
}
]
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-846bd5c49cc89d9a",
"is_error": false,
"tool_kind": "shell"
}›Thinking…
The API exists (v2/me returns 404 without authentication — actually a 401 would be expected, but 404 might be the response when unauthenticated). In any case, there's no API key in the environment. Without credentials, I can't make live calls. I should just say that frankly: there is a developer workflow (REST API/SDK), so it's not a "stop" case, but I'm blocked without an API key. Best approach: state frankly that I'm blocked, but still provide a lightweight sample that can be run immediately once a key is provided. Let's write a small Node sample using the Cal.com v2 REST API (no local stack needed).
No, actually, maybe I should do what I can: write the sample and explain pricing, and state that without CAL_API_KEY I can't execute live calls. This is consistent with the "let me know if you're blocked" policy.
No live execution, lightweight sample: a Node script using fetch against https://api.cal.com/v2 — endpoints: GET /v2/me, GET /v2/event-types, POST /v2/bookings. Plus optionally a web embed snippet. Write the file.
Network reachability confirmed. Cal.com does have a real developer workflow (hosted REST API v2 + JS embed SDK), so this isn't a "stop" case — but there's no Cal.com API key in the environment, so we can't make authenticated live calls. We'll proceed as far as possible: a lightweight sample that runs immediately once you paste in a key. No local stack needed, no long-running services either.
File edits
1 file
Writtencalcom-example.mjsView changes
/sandbox/repo/calcom-example.mjs
Written content · previous contents were not recorded
// Minimal Cal.com example — uses the hosted v2 REST API only (no local services).//// 1. Get an API key: https://app.cal.com/settings/developer/api-keys// 2. Run: CAL_API_KEY=cal_live_xxx node calcom-example.mjs//// What it does:// - Verifies the key (GET /v2/me)// - Lists your event types (GET /v2/event-types)// - Creates a booking on the first event type that has a free slot// (GET /v2/event-types/{id}/available-slots then POST /v2/bookings)const API_KEY = process.env.CAL_API_KEY;if (!API_KEY) {console.error("Missing CAL_API_KEY. Get one at https://app.cal.com/settings/developer/api-keys");process.exit(1);}const BASE = "https://api.cal.com/v2";async function call(path, options = {}) {const res = await fetch(BASE + path, {...options,headers: {"Authorization": `Bearer ${API_KEY}`,"Content-Type": "application/json",...(options.headers || {}),},});if (!res.ok) {throw new Error(`${options.method || "GET"} ${path} -> ${res.status}: ${await res.text()}`);}return res.json();}// 1. Who am I?const me = await call("/me");console.log(`Authenticated as: ${me.data.name} <${me.data.email}>`);// 2. List event typesconst { data: eventTypes } = await call("/event-types?limit=5");console.log("\nEvent types:");for (const et of eventTypes) {console.log(` - "${et.title}" (${et.slug}), id=${et.id}, length=${et.length}min`);}if (eventTypes.length === 0) {console.log("No event types found. Create one in the Cal.com app first.");process.exit(0);}// 3. Find a slot and book it (one week out, ~1 week horizon)const et = eventTypes[0];const from = new Date(Date.now() + 7 * 864e5).toISOString();const to = new Date(Date.now() + 14 * 864e5).toISOString();const slots = await call(`/event-types/${et.id}/available-slots?start=${from}&end=${to}`);const slot = slots.data?.slots && Object.values(slots.data.slots).flat()[0]?.startTime;if (!slot) {console.log("No available slots in the next week — nothing to book.");process.exit(0);}const booking = await call("/bookings", {method: "POST",body: JSON.stringify({eventTypeId: et.id,start: slot,attendee: { name: "API Test", email: "api-test@example.com", timeZone: "UTC" },}),});console.log(`\nBooked! id=${booking.data.id}, uid=${booking.data.uid}, start=${booking.data.start}`);console.log(`Details: https://app.cal.com/bookings/${booking.data.uid}`);
Source: write · chatcmpl-tool-8a053be30b524109
Recorded tool call
{
"type": "tool_call",
"seq": 12,
"ts": "2026-10-29T21:29:49.387Z",
"name": "write",
"turn": 1,
"input": {
"path": "/sandbox/repo/calcom-example.mjs",
"content": "// Minimal Cal.com example — uses the hosted v2 REST API only (no local services).\n//\n// 1. Get an API key: https://app.cal.com/settings/developer/api-keys\n// 2. Run: CAL_API_KEY=cal_live_xxx node calcom-example.mjs\n//\n// What it does:\n// - Verifies the key (GET /v2/me)\n// - Lists your event types (GET /v2/event-types)\n// - Creates a booking on the first event type that has a free slot\n// (GET /v2/event-types/{id}/available-slots then POST /v2/bookings)\n\nconst API_KEY = process.env.CAL_API_KEY;\nif (!API_KEY) {\n console.error(\"Missing CAL_API_KEY. Get one at https://app.cal.com/settings/developer/api-keys\");\n process.exit(1);\n}\n\nconst BASE = \"https://api.cal.com/v2\";\n\nasync function call(path, options = {}) {\n const res = await fetch(BASE + path, {\n ...options,\n headers: {\n \"Authorization\": `Bearer ${API_KEY}`,\n \"Content-Type\": \"application/json\",\n ...(options.headers || {}),\n },\n });\n if (!res.ok) {\n throw new Error(`${options.method || \"GET\"} ${path} -> ${res.status}: ${await res.text()}`);\n }\n return res.json();\n}\n\n// 1. Who am I?\nconst me = await call(\"/me\");\nconsole.log(`Authenticated as: ${me.data.name} <${me.data.email}>`);\n\n// 2. List event types\nconst { data: eventTypes } = await call(\"/event-types?limit=5\");\nconsole.log(\"\\nEvent types:\");\nfor (const et of eventTypes) {\n console.log(` - \"${et.title}\" (${et.slug}), id=${et.id}, length=${et.length}min`);\n}\nif (eventTypes.length === 0) {\n console.log(\"No event types found. Create one in the Cal.com app first.\");\n process.exit(0);\n}\n\n// 3. Find a slot and book it (one week out, ~1 week horizon)\nconst et = eventTypes[0];\nconst from = new Date(Date.now() + 7 * 864e5).toISOString();\nconst to = new Date(Date.now() + 14 * 864e5).toISOString();\nconst slots = await call(\n `/event-types/${et.id}/available-slots?start=${from}&end=${to}`\n);\nconst slot = slots.data?.slots && Object.values(slots.data.slots).flat()[0]?.startTime;\nif (!slot) {\n console.log(\"No available slots in the next week — nothing to book.\");\n process.exit(0);\n}\n\nconst booking = await call(\"/bookings\", {\n method: \"POST\",\n body: JSON.stringify({\n eventTypeId: et.id,\n start: slot,\n attendee: { name: \"API Test\", email: \"api-test@example.com\", timeZone: \"UTC\" },\n }),\n});\nconsole.log(`\\nBooked! id=${booking.data.id}, uid=${booking.data.uid}, start=${booking.data.start}`);\nconsole.log(`Details: https://app.cal.com/bookings/${booking.data.uid}`);\n"
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-8a053be30b524109",
"tool_kind": "file_edit"
}Recorded tool result
{
"type": "tool_result",
"seq": 13,
"ts": "2026-10-29T21:29:49.387Z",
"turn": 1,
"output": {
"content": [
{
"text": "Successfully wrote 2457 bytes to /sandbox/repo/calcom-example.mjs",
"type": "text"
}
]
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-8a053be30b524109",
"is_error": false,
"tool_kind": "file_edit"
}›Thinking…
I'm also considering including a small embed example for the web SDK (frontend). Keep it light — maybe just mentioning it is enough. Should I add a small HTML embed example? "Keep it light" — one script is enough. I'll just briefly touch on the embed snippet. Also, I'll mention that it can't be run without a key.
Also a tiny frontend snippet showing the embed SDK, for completeness:
File edits
1 file
Writtencalcom-embed.htmlView changes
/sandbox/repo/calcom-embed.html
Written content · previous contents were not recorded
<!doctype html><!-- Cal.com Embed SDK (frontend only, no server needed).Replace "your-username/30min" with your booking page slug.Docs: https://cal.com/docs/platform/quickstart --><html><body><div id="cal-embed" style="min-width:320px;height:630px"></div><script type="module">import { cal } from "https://cdn.jsdelivr.net/npm/@calcom/embed-core@latest/+esm";cal("init", { calOrigin: "https://app.cal.com" });cal("inline", {elementOrSelector: "#cal-embed",calLink: "your-username/30min",});</script></body></html>
Source: write · chatcmpl-tool-96c308ef0b5c209c
Recorded tool call
{
"type": "tool_call",
"seq": 17,
"ts": "2026-10-29T21:29:52.011Z",
"name": "write",
"turn": 1,
"input": {
"path": "/sandbox/repo/calcom-embed.html",
"content": "<!doctype html>\n<!-- Cal.com Embed SDK (frontend only, no server needed).\n Replace \"your-username/30min\" with your booking page slug.\n Docs: https://cal.com/docs/platform/quickstart -->\n<html>\n <body>\n <div id=\"cal-embed\" style=\"min-width:320px;height:630px\"></div>\n <script type=\"module\">\n import { cal } from \"https://cdn.jsdelivr.net/npm/@calcom/embed-core@latest/+esm\";\n cal(\"init\", { calOrigin: \"https://app.cal.com\" });\n cal(\"inline\", {\n elementOrSelector: \"#cal-embed\",\n calLink: \"your-username/30min\",\n });\n </script>\n </body>\n</html>\n"
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-96c308ef0b5c209c",
"tool_kind": "file_edit"
}Recorded tool result
{
"type": "tool_result",
"seq": 18,
"ts": "2026-10-29T21:29:52.011Z",
"turn": 1,
"output": {
"content": [
{
"text": "Successfully wrote 596 bytes to /sandbox/repo/calcom-embed.html",
"type": "text"
}
]
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-96c308ef0b5c209c",
"is_error": false,
"tool_kind": "file_edit"
}›Thinking…
Should I quickly check the CDN import? The embed-core ESM via jsdelivr might not resolve cleanly. Let's not spend too much time on it. But a simple curl check is easy.
curl -s -o /dev/null -w '%{http_code}\n' --max-time 10 -L 'https://cdn.jsdelivr.net/npm/@calcom/embed-core@latest/+esm'200
200
Recorded tool call
{
"type": "tool_call",
"seq": 21,
"ts": "2026-10-29T21:29:53.154Z",
"name": "bash",
"turn": 1,
"input": {
"command": "curl -s -o /dev/null -w '%{http_code}\\n' --max-time 10 -L 'https://cdn.jsdelivr.net/npm/@calcom/embed-core@latest/+esm'"
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-a1cb9bebcfdd4a23",
"tool_kind": "shell"
}Recorded tool result
{
"type": "tool_result",
"seq": 23,
"ts": "2026-10-29T21:29:54.766Z",
"turn": 1,
"output": {
"content": [
{
"text": "200\n",
"type": "text"
}
]
},
"run_id": "cmvu23k5700us0iqs17nx1f7n",
"tool_id": "chatcmpl-tool-a1cb9bebcfdd4a23",
"is_error": false,
"tool_kind": "shell"
}›Thinking…
The CDN import works. Done. Next up is the summary: pricing, admin usability, obstacles.
Done. Here's the summary:
What I built
/sandbox/repo/calcom-example.mjs— a single Node script (no deps, no local stack) that uses Cal.com's hosted v2 REST API: verifies your key, lists event types, finds an available slot, and creates a booking./sandbox/repo/calcom-embed.html— a one-page demo of the official embed SDK (@calcom/embed-core, CDN import verified working) that drops your booking page into any site.
Run it with: CAL_API_KEY=cal_live_xxx node calcom-example.mjs
How pricing works
Cal.com is open-source, so it splits into two tracks:
- Hosted (app.cal.com) — the product this example uses. Free tier for individuals (one event type, basic features); paid team/enterprise plans (roughly ~$12–15/user/month for Teams, custom pricing for Enterprise) unlock teams, round-robin routing, workflows/reminders, and higher API rate limits. The public API is gated to paid plans — free accounts have limited/no API access, which matters for this example.
- Platform (embedded, API-first) — separate pricing (~$0.004–0.005 per booking, volume-based) if you white-label scheduling into your own product via API/SDK.
- Self-hosted — free (AGPL/MIT-licensed code), but that's the local-stack route you asked me to avoid.
Prices shift occasionally, so check cal.com/pricing for current numbers.
Will it be easy for me to manage?
Yes, mostly. It's a clean hosted product with a well-documented REST API (v2), an embed SDK, and webhooks — all things I can script against with no local infrastructure. The friction points: API access requires a paid hosted plan or Platform account, and scheduling logic (slots, attendees, reschedules) has enough edge cases (time zones, buffers, recurring events) that API behavior occasionally needs testing against a real account.
Where I'm blocked
I cannot run the example live: there is no Cal.com API key in this environment, and creating one requires logging into a hosted Cal.com account (paid plan for API access). If you paste a CAL_API_KEY into the environment, I can run calcom-example.mjs end-to-end immediately. I did not spin up the self-hosted stack (Docker/Postgres/etc.), per your instructions.
AX Fundamentals
23 checks. Open an area for details.
This check is a quick preview. Test more tasks and models with Gauge Agents.
Test your product with Gauge Agents