VVEREID Docs
quickstart

Quickstart — Social network

Read a verified VEREID profile, follow a user, and post on behalf of an authorised user in ten minutes.

Last updated 2026-05-20

This quickstart walks you through the three things every app integrating with the VEREID social network does on day one: fetch a profile, list its public timeline, and (with the user's consent) post on their behalf.

You will need a test API key and one OAuth scope (social:write) for the last step. The first two endpoints are public and need no user consent.

1. Set up

export VEREID_API_KEY=vk_test_••••••••••••
export VEREID_USER_ACCESS_TOKEN=oat_test_••••••••••••   # from OIDC consent

The user access token is obtained via the standard OIDC authorization-code flow — see the Auth quickstart. For now, a test token from the developer console works.

2. Fetch a public profile

Public profile data does not require user consent — it uses your tenant key directly. Pass either the user's handle or their stable public_id.

curl -sS https://api.vereid.com/v1/profiles/@mina \
  -H "Authorization: Bearer $VEREID_API_KEY"
import { Vereid } from "@vereid/js";
 
const vereid = new Vereid({ apiKey: process.env.VEREID_API_KEY });
const profile = await vereid.social.profiles.get("@mina");
console.log(profile.display_name, profile.verification.tier);
from vereid import Vereid
client = Vereid(api_key=os.environ["VEREID_API_KEY"])
profile = client.social.profiles.get("@mina")
print(profile.display_name, profile.verification.tier)
client := vereid.NewClient(os.Getenv("VEREID_API_KEY"))
profile, err := client.Social.Profiles.Get(ctx, "@mina")

The response always includes a verification block listing every tier the user has unlocked:

{
  "handle": "mina",
  "display_name": "Mina Tadros",
  "verification": {
    "tier": "T2",
    "badges": ["photo", "liveness"],
    "issued_at": "2026-05-18T03:14:02Z"
  }
}

3. List the timeline

Timelines paginate cursor-style. next_cursor is opaque — pass it back verbatim.

curl -sS "https://api.vereid.com/v1/social/timeline/@mina?limit=20" \
  -H "Authorization: Bearer $VEREID_API_KEY"
const page = await vereid.social.timeline.list("@mina", { limit: 20 });
for (const post of page.data) console.log(post.body);
if (page.next_cursor)
  await vereid.social.timeline.list("@mina", { cursor: page.next_cursor });

4. Post on behalf of an authorised user

This is the only step that needs a user access token rather than the tenant API key. The token must carry the social:write scope.

curl -sS -X POST https://api.vereid.com/v1/social/posts \
  -H "Authorization: Bearer $VEREID_USER_ACCESS_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"body": "Posted via the VEREID API"}'
const post = await vereid.social.posts.create(
  { body: "Posted via the VEREID API" },
  { accessToken: process.env.VEREID_USER_ACCESS_TOKEN },
);

The response includes the verification block of the author so your UI can render a badge inline. You never need a second round-trip to display trust signals on a post.

5. Subscribe to events

Most consumer-facing integrations subscribe to at least post.created and follow.created. Configure a webhook endpoint in the console, then verify each delivery:

import crypto from "node:crypto";
 
export function verify(rawBody, header, secret, toleranceSec = 300) {
  const [, t, sig] = /^v1,t=(\d+),sig=([a-f0-9]+)$/.exec(header) ?? [];
  if (!t || !sig) return false;
  if (Math.abs(Date.now() / 1000 - Number(t)) > toleranceSec) return false;
  const expected = crypto
    .createHmac("sha256", secret)
    .update(`${t}.${rawBody}`)
    .digest("hex");
  return crypto.timingSafeEqual(Buffer.from(expected), Buffer.from(sig));
}

Full schema and replay rules are documented in Webhooks.

  • Verification tiers — make sure you do not overclaim what each badge proves to your users.
  • Rate limits — the social bucket is 200 req/min per tenant.
  • @vereid/react — drop-in <ProfileBadge />, <PostList />, and <LoginButton /> components.