DEV Community

Ujjwal Dubey
Ujjwal Dubey

Posted on

A Workflow Audit as Data: A Small JSON Schema for Steps, Owners and Exceptions

When an owner asks a developer to "add AI", the first useful deliverable is not a model call. It is a structured record of how the work happens today. This post shows a small schema I use, so that knowing how to audit a business workflow before buying AI as structured data becomes something you can diff, review and test against.

The schema

{
  "workflow": "new_enquiry_reply",
  "trigger": {"channel": "whatsapp", "event": "inbound_message"},
  "source_of_truth": {"contact": "crm", "stock": "sheet"},
  "steps": [
    {"id": "s1", "actor": "human:front_desk", "action": "read_message", "tool": "whatsapp", "waits": "until free"},
    {"id": "s2", "actor": "human:front_desk", "action": "lookup_contact", "tool": "crm"},
    {"id": "s3", "actor": "human:owner", "action": "approve_price", "tool": "phone", "waits": "until owner free"}
  ],
  "exceptions": [
    {"case": "voice_note", "today": "front desk listens later"},
    {"case": "repeat_customer_new_number", "today": "duplicate contact created"}
  ],
  "must_stay_human": ["price", "refund", "cancellation"],
  "success_metric": "median_first_reply_minutes"
}
Enter fullscreen mode Exit fullscreen mode

A tiny validator

Keep it in the same repo and run it in CI, so a half-filled audit cannot be merged.

import json, sys

REQUIRED = {"workflow", "trigger", "source_of_truth", "steps",
            "exceptions", "must_stay_human", "success_metric"}

doc = json.load(open(sys.argv[1]))
missing = REQUIRED - doc.keys()
assert not missing, f"missing: {missing}"
assert len(doc["exceptions"]) >= 5, "add more real exceptions"
for s in doc["steps"]:
    assert s["actor"].split(":")[0] in ("human", "system"), s
print("ok:", doc["workflow"], len(doc["steps"]), "steps")
Enter fullscreen mode Exit fullscreen mode

Why this helps before buying anything

  • Exceptions become test cases. Every item in exceptions is a scenario a vendor must run before you sign.
  • Approval gates are explicit. must_stay_human stops a tool from quietly sending prices.
  • Source of truth is named. If two systems claim to own the contact, you have found your first bug.
  • Waits are visible. The waits field shows where customers sit idle, which is usually where the value is.
  • It diffs. When the process changes, the pull request shows exactly what changed.

How to fill it

Interview the people who do the job, not their manager. Copy real cases from the last few weeks of messages into exceptions, with personal details removed. Do not tidy them.

What to do with it

Hand the file to each vendor and ask which steps they automate, which they leave to people, and how they log failures. If a vendor cannot answer per step, that is your answer.

Disclosure: I co-founded NxFlowAI (Mumbai). We produce something like this in our first audit, which takes 72 hours for one workflow.

Top comments (0)