SDK overview

Huudis ships official SDKs for Node.js, Python and Go. All three have client.api (client.API in Go): one method per Huudis API route, generated from the API spec, so every feature is reachable. Each call carries the credential its route takes — see Credentials.

Node.js Python Go
Every API route client.api.<area><Action>() client.api.<area>_<action>() client.API.<Area><Action>(ctx, …)
Access-key signing ✓ ✓ ✓
Client credentials (/app/*) ✓ ✓ ✓
OIDC sign-in helpers ✓ ✓ ✓
verifyAccessToken (JWT + JWKS) ✓ ✓ ✓
Webhook signature check ✓ ✓ ✓
Typed resource namespaces client.iam.listUsers() client.iam.list_users() client.IAM.ListUsers(ctx, …)

Install

Language Command
Node.js npm install @forjio/huudis-node
Python pip install forjio-huudis (import huudis)
Go go get github.com/hachimi-cat/huudis-go

See Installation for prerequisites.

Credentials

Routes Credential Node.js Python Go
Everything a signed-in person may call The person's bearer token session session Token, or per call RequestAuth
/account/*, /iam/*, /authz/* for programs An IAM access key, each request signed Huudis-HMAC-SHA256; acts as the key's user within the user's IAM policies accessKey access_key_id, secret_access_key AccessKeyID, SecretAccessKey
/app/* Your OIDC app's client credentials clientId, clientSecret client_id, client_secret ClientID, ClientSecret

All three read the same environment: HUUDIS_ISSUER, HUUDIS_ACCESS_KEY_ID + HUUDIS_SECRET_ACCESS_KEY, HUUDIS_CLIENT_ID + HUUDIS_CLIENT_SECRET, HUUDIS_WORKSPACE_ID (the workspace to act in), and Go also HUUDIS_TOKEN. A person's token wins over a key. Which routes a key may call, and the ones it never may: API authentication.

Call the API

Node.js:

import { HuudisClient } from '@forjio/huudis-node';

const huudis = new HuudisClient({
  issuer: 'https://huudis.com',
  accessKey: { accessKeyId: process.env.HUUDIS_ACCESS_KEY_ID, secretAccessKey: process.env.HUUDIS_SECRET_ACCESS_KEY },
});
const users = await huudis.api.iamUsers();
await huudis.api.iamCreateGroups({ name: 'On call' });

Python:

from huudis import HuudisClient

huudis = HuudisClient(issuer="https://huudis.com", access_key_id="AKIA…", secret_access_key="…")
users = huudis.api.iam_users()
huudis.api.iam_create_groups(name="On call")

Go:

import huudis "github.com/hachimi-cat/huudis-go"

c, err := huudis.NewClient(huudis.ClientOptions{Issuer: "https://huudis.com", AccessKeyID: "AKIA…", SecretAccessKey: "…"})
users, err := c.API.IamUsers(ctx)
_, err = c.API.IamCreateGroups(ctx, &huudis.IamCreateGroupsArgs{Name: "On call"})

Every Go client.API method is listed on Every route (client.API), the typed resources under Go SDK resources; every route's fields are in the API reference.

OIDC sign-in

Construct the client with your OIDC app's clientId (and clientSecret for a confidential client), then:

Step Node.js Python Go
Send the user to Huudis authorizationUrl({ redirectUri, state, codeChallenge? }) authorization_url(redirect_uri=, state=, code_challenge=) AuthorizationURL(AuthorizationURLOptions{…})
Exchange the code in your callback exchangeCode({ code, redirectUri, codeVerifier? }) exchange_code(code=, redirect_uri=, code_verifier=) ExchangeCode(ctx, code, redirectURI, codeVerifier)
Refresh refreshAccessToken(refreshToken) refresh_access_token(refresh_token) RefreshAccessToken(ctx, refreshToken)
Profile userInfo(accessToken) userinfo(access_token) UserInfo(ctx, accessToken)

Verify tokens

import { verifyAccessToken } from '@forjio/huudis-node';

// Reads HUUDIS_ISSUER and HUUDIS_AUDIENCE (your client id); fetches and caches the JWKS.
const claims = await verifyAccessToken(req.headers.authorization);

Python: from huudis import verify_access_token. Go: huudis.VerifyAccessToken(ctx, header, huudis.VerifyOptions{}).

Verify webhook signatures

When Huudis posts an event to your endpoint it sends X-Huudis-Signature: t=<unix>,v1=<hex>. Verify with the raw request body bytes:

import { verifyWebhookSignature } from '@forjio/huudis-node';
import express from 'express';

app.post('/webhooks/huudis', express.raw({ type: 'application/json' }), (req, res) => {
  const ok = verifyWebhookSignature(req.body, req.header('X-Huudis-Signature') ?? '', process.env.HUUDIS_WEBHOOK_SECRET);
  if (!ok) return res.sendStatus(400);
  res.sendStatus(204);
});

Python: verify_webhook_signature(raw_body, header, secret). Go: huudis.VerifyWebhookSignature(rawBody, header, secret, nil).

Source

Next