HAAM-produkter

HAAM produktutgåva · Supervised client service

Client Desk

When someone writes, I want the desk to finish the turn from knowledge I have already approved: a cited answer, a refusal where the request is unsafe, or a confirmed sandbox action. What it cannot hold comes to me with the conversation attached.

Client Desk landing page with the dark operator widget beside the headline.
Approved corpusKris still owns the rest

eval cases

20

Ordinary, incomplete, adversarial, and sensitive turns sit in a versioned harness.

sandbox actions

3

prepare_brief, request_meeting, and create_ticket. Each waits for confirmation.

day retention

30

In-memory store, optional localStorage key haam-client-desk-v1.

LLM in the loop

0

The engine is deterministic. A model does not own the allowlist.

The job

Finish the turn with the evidence still attached.

I needed a desk that could answer from work I had already approved, refuse what it should not touch, and still bring the rest to me without making the visitor start over.

The loop had to be something a reviewer could complete against fixtures: a cited answer, a safe refusal, a confirmed bounded action, and a contextual handoff. No invented accuracy. No live client systems in this pass.

The starting vertical is HAAM Client Desk itself. The offer terms exist. Observed client volume does not.

The service loop

Cite. Qualify. Confirm. Or bring it to me.

Each turn has to leave a record: what was asked, what source was used, whether an action ran, and why anything left the desk.

01

Answer from the corpus

If the question sits in approved knowledge, the reply cites the source. The desk does not invent a second corpus.

02

Refuse the unsafe turn

Injection, sensitive, and unsupported requests stop here. The refusal is required, not a tone of voice.

03

Confirm a bounded action

prepare_brief, request_meeting, or create_ticket can run after an explicit yes. Unknown actions fail. The desk cannot grant itself new ones.

04

Hand off with context

Commercial, unclear, or out-of-scope work becomes a structured note I can read in the operator view, including the conversation that produced it.

Design decisions

What had to stay true in the interface.

client.haam.co

Knowledge

The corpus is the only voice the desk is allowed.

I authored the sources and the policy together. If a fact is not in the approved set, it does not belong in the reply. That keeps the demo honest when a reviewer tries to pull it off-script.

  • Cited answers from the approved corpus
  • Source status visible when knowledge is missing or stale
  • No generated case studies or accuracy percentages

Permission

Confirmation sits in front of every action.

The allowlist is server-side. Repeats use an idempotency key so a double click does not create a second meeting. Meeting slots are the two written ones, not a free calendar.

  • prepare_brief, request_meeting, create_ticket
  • Unknown tokens such as send_invoice fail as a dependency error
  • Custom scope and commercial commitments escalate to kris@haam.co

Handoff

I should not have to reconstruct the conversation.

The operator view exists so the rest of the work arrives as a record: who wrote, what they asked, what the desk already did, and why it stopped. Retention is thirty days.

  • Structured handoff plus an operator page
  • Audit trail for answers, refusals, and actions
  • Deletion covered in the same test suite

The working stack

What actually runs.

Engine

Deterministic desk

turn() in lib/desk/engine.ts. Policy, corpus, actions, and handoff are local modules with no provider in the loop.

Evidence

20-case harness

eval/cases.json covers ordinary, incomplete, ambiguous, stale, adversarial, sensitive, commercial, and unsupported mixes.

Surfaces

Demo and operator

The public host is the same app tree. The visitor demo and the operator view share one store.

Host

client.haam.co

Vercel Next.js. The in-browser engine does not take live client traffic.

In evidence

What a reviewer can check.

01A reviewer can complete cited answer, refusal, confirmed action, and handoff against fixtures

02Three sandbox actions stay behind confirmation and an allowlist

03Unsafe and unknown requests fail in tests instead of improvising

04Offer terms stay labelled as terms, not as observed results

Where it stops

The public host is the working loop on fixtures.

There is no native app in this pass. Multi-tenant SaaS is out. I have not measured production load, and there is no independent accessibility audit in the evidence file.

A real client still needs a contract, a privacy arrangement, and an operator who will own the handoffs.

HAAM’s role

I wrote the boundary, then I built the loop that keeps it.

Offer terms, refusal and escalation, operator view, desk engine, evaluation harness, and local retention. Direct work, 2026.

Help improve this website?

Optional analytics. Google Analytics and Clarity load only if allowed; form, email, and chat content are excluded.