Connector API · v1

Build a connector. Give your agent real data.

A SupportCore connector is a small HTTPS service you host. It lets your support agent look up live data and run the actions you allow — order status, returns, warranty, account changes — all declared by a manifest so SupportCore discovers your capabilities automatically. One contract, any stack, no custom work on our side.

01Quick start

01

Host the endpoint

Serve a small service at /supportcore/v1 over HTTPS, guarded by a bearer key.

02

Publish a manifest

Declare your lookups and actions at GET /manifest. Each becomes an agent tool.

03

Connect it

Paste the base URL + key into Console → Connections. Your agent starts using it.

02Authentication

SupportCore sends a bearer key you issue in the Connections tab. Verify it on every request; reject anything else.

every request from SupportCore
POST https://api.yourapp.com/supportcore/v1/lookup/customer
Authorization: Bearer sc_live_9f2c…a71b
Content-Type: application/json
Idempotency-Key: e0b6…c455   # on actions; safe to retry

HTTPS only. Compare the key in constant time; return 401 on mismatch. Rotate it from the Connections tab any time — no redeploy. Optionally verify an X-SupportCore-Signature HMAC of the body.

03The manifest — where you define capabilities

The heart of the spec. SupportCore fetches your manifest and turns every entry into a tool the agent can use. To teach the agent a new action — say, a note on an order — add one object here and implement its endpoint. That's it.

GET/supportcore/v1/manifest
{
  "connector": "YourApp", "version": "1.0",
  "lookups": [
    { "id": "customer", "title": "Customer profile",
      "description": "Plan, status and recent activity for an email",
      "params": [ { "name": "email", "type": "string", "required": true } ],
      "returns": "plan, status, signup_date, last_active" }
  ],
  "actions": [
    { "id": "add_order_note", "title": "Add a note to an order",
      "params": [ { "name": "order_id", "type": "string", "required": true, "pattern": "^[0-9]+$" },
                 { "name": "note", "type": "string", "required": true } ],
      "approval": "optional", "reversible": true },
    { "id": "cancel_subscription", "title": "Cancel a subscription",
      "params": [ { "name": "email", "type": "string", "required": true } ],
      "approval": "required", "reversible": false }
  ]
}
FieldMeaning
idStable name. SupportCore calls /lookup/{id} or /action/{id}. Never rename a live id.
params[]Each: name, type, required, optional pattern (regex). SupportCore validates against pattern before calling you.
approvalrequired gates the action behind a human click. Default required when omitted.
reversibleIrreversible actions always get an extra confirm and never auto-run.

04Lookups · read

Return support-relevant, non-sensitive data. On no match, return 200 with { "found": false } — not a 404.

POST/supportcore/v1/lookup/customer
request
{ "email": "kees@example.com" }
200 response
{ "found": true,
  "data": { "plan": "Pro", "status": "active",
            "open_invoices": 0 } }

05Actions · write

The logic and permission checks live in your backend — SupportCore only requests it. Return a short human message; the agent may quote it. Honour Idempotency-Key so the same key never acts twice.

POST/supportcore/v1/action/cancel_subscription
request
{ "email": "kees@example.com",
  "_meta": { "approved_by": "stephen@urenapp.eu",
            "ticket": "89155065-…" } }
200 response
{ "ok": true,
  "message": "Cancelled, effective 1 Aug.",
  "reference": "CANCEL-7731" }
Destructive actions (refunds, deletions) should be approval:"required" and reversible:false. SupportCore never auto-runs these — a human confirms first. On a business-rule failure, return 200 with { "ok": false, "message": "…" } so the agent can explain it.

06Reference data & follow-up questions

The agent is only as good as what it can see. Two kinds of lookups make it genuinely helpful:

Record lookups — “this specific customer / order”

Keyed by an identifier (email, order id). We strongly recommend backing these with a read-only database account — grant SELECT on just the tables or views support needs (customers, orders, bookings, invoices) so the agent can see history and status without any write access or exposure of sensitive fields.

Catalogue lookups — “what do we even offer?”

Expose your options too, not just records. A hotel publishes a room_types lookup (types, capacity, price); a shop publishes shipping_options. This is what lets the agent reason and ask the right follow-up instead of guessing.

Worked example — a hotel. A guest writes “a room for 2, what does it cost?” The agent calls room_types, sees that pricing depends on dates and room type, notices the guest gave neither, and replies asking for them — then, once answered, prices it exactly. You didn't script that conversation; you just published the catalogue and the agent did the reasoning.

Rule of thumb: if a human agent would need to look something up or ask a clarifying question to answer, publish a lookup for it. The agent will use it the same way.

07Errors & limits

RuleDetail
LatencyRespond within 5 seconds — SupportCore times out after that.
ErrorsHTTP status for transport/auth/server; { ok:false } for business outcomes. Shape: { "error": { "code", "message" } }.
VersioningPin the major version in the path (/v1/). Add fields freely; never remove one within a version.
Rate limitReturn 429 when needed — SupportCore backs off and retries.

08Security

  • Least privilege. Read-only for lookups; writes only through the specific operations your actions implement. Never an admin account.
  • Expose only what support needs. No password hashes, full card numbers or unrelated personal data — even behind a valid key.
  • Validate server-side. The manifest pattern is a first gate; re-check ownership and entitlements in your handler.
  • Rotate & log. Rotate the key; log every call with its ticket and approved_by.

09Full minimal example

connector.js — a complete, compliant connector
const app = require("express")(); app.use(require("express").json());
const KEY = process.env.SUPPORTCORE_KEY;

app.use((req, res, next) => {                       // 1 · auth
  const t = (req.headers.authorization || "").replace("Bearer ", "");
  if (t !== KEY) return res.status(401).json({ error: { code: "unauthorized" } });
  next();
});

app.get("/supportcore/v1/manifest", (_, res) => res.json({   // 2 · manifest
  connector: "YourApp", version: "1.0",
  lookups: [{ id: "customer", title: "Customer profile",
              params: [{ name: "email", type: "string", required: true }] }],
  actions: [{ id: "add_order_note", title: "Add order note", approval: "optional",
              params: [{ name: "order_id", type: "string", required: true, pattern: "^[0-9]+$" },
                       { name: "note", type: "string", required: true }] }]
}));

app.post("/supportcore/v1/lookup/customer", async (req, res) => {  // 3 · lookup
  const u = await db.user(req.body.email);
  res.json(u ? { found: true, data: { plan: u.plan, status: u.status } } : { found: false });
});

app.post("/supportcore/v1/action/add_order_note", async (req, res) => {  // 4 · action
  await db.addNote(req.body.order_id, req.body.note);
  res.json({ ok: true, message: "Note added to order " + req.body.order_id });
});

app.listen(8080);

10Readiness checklist

  • HTTPS at a stable /supportcore/v1 base URL.
  • GET /manifest lists every lookup and action; each id has a handler.
  • Bearer auth enforced; 401 on mismatch; key rotatable.
  • Lookups return { found, data }; actions { ok, message }; under 5s.
  • Idempotency on actions; destructive ones approval:"required".
  • Read-only, least-privilege data; no sensitive fields exposed.
Ready? Paste your base URL and key into Console → Connections → Add connector. SupportCore reads your manifest and your agent starts answering with real data.