What it does

ABC Vision is a badminton coaching agent that refuses to guess who you are.

Give it a match video and it finds the rallies with OpenCV 5, works out which player on court is you, and reports how you played. When it cannot do that confidently, it says so and shows you the evidence instead of publishing a number it does not believe.

It is live. Open it and watch it fail honestly:

The conversation on the left of that page is staged. Every call on the right is real - ten JSON-RPC calls from your browser to the MCP server, each openable to its raw request and response. The page is served from the same origin as /mcp, so there is no proxy in between and nothing that could be a recording.

Why declining is the product

A skill rating is a claim about a person. Get it wrong and you have told someone they are worse than they are, in front of their club.

So this engine is built to decline, and it is not hypothetical. Over 1,117 real production jobs between 2026-09-06 and 2026-09-17:

Outcome Jobs
Jobs that produced a report 705
Published a skill level 390 (55.3% of reported)
Declined to publish 301 (42.7% of reported)
Largest single reason too little of the player could be tracked - 213 (30.2% of reported)

Every percentage this project reports carries both denominators, every time, because a percentage without one is a way of being wrong on purpose.

The agent loop

Identifying a player is not a classification. It is a search, and the vision result decides what gets searched next:

  1. open_identity_session - register the detections and appearance signatures
  2. propose_identity - anchor somewhere, propose who the subject is
  3. score_identity_plan - how many rallies does that plan actually cover?
  4. Below the gate? Exclude that anchor and propose again - a measured visual result changing the next tool call
  5. Out of anchors? compare_identity_plans, then explain_identity_difference, then ask the human

The demo runs twice. First the ordinary case, where the player is on court for all three rallies: identity locks on the first attempt and analysis proceeds. Then the harder one, where the player rotates off court for the third and no assignment of detections to people can cover a rally the player was not in -- the loop tries every anchor, reaches 2 of 3, and asks rather than publishes. Only the second run branches, and the branch is the point.

OpenCV 5 on AWS, verifiable by you

Call protocol_info on the endpoint above and it returns the OpenCV version of the process that answered:

"opencv_version": "5.0.0",
"opencv_module": "/usr/local/lib/python3.12/site-packages/cv2/__init__.py"

Opening /mcp in a browser returns a JSON-RPC error about a missing session ID. That is correct - it is a protocol endpoint, not a web page. The page is at /.

The scan path imports only cv2, numpy and the standard library - no PyTorch, no ONNX Runtime, no MediaPipe - which is why real video analysis fits in a 227 MB container instead of a multi-gigabyte one.

Architecture: CloudFront for TLS, an EC2 container behind it, pulling from a private ECR repository in our own account. The security group admits only CloudFront's origin-facing prefix list. There is no SSH and no key pair exists; administration is SSM Session Manager.

Privacy is structural, not a policy

The analysis engine is never committed and never leaves the owner's AWS account. A named allowlist of eleven files is staged at build time, the build refuses to run if anything resembling customer data reaches it, and the same refusal runs again inside CodeBuild - the last point before an image exists, because a pushed image cannot be un-pushed.

The decision trace redacts by key name and replaces identifiers with truncated SHA-256 handles, so two calls about the same video are still recognisably the same video without naming it. Redaction is covered by tests, not by convention.

What we got wrong

docs/CORRECTIONS.md in the repository lists what this project published and then found to be wrong - including three errors the submission made about itself. The protocol version in an earlier draft was overstated; DNS rebinding protection was assumed to be on and was off. The conformance checker we built for the Open Source mini challenge caught both.

It did not catch the third, and nothing else automated did either: a claim about our own failure handling that the dataset shipped in the repository contradicts. People found it by reading the claim against the data, after it had already shipped.

A project whose entire argument is about not overclaiming should publish its own corrections. So it does.

Built With

Share this project:

Updates

Submission history