CAPNS Documentation
A naming system for computational capabilities
Overview
CAPNS (Capability Namespace System) gives computational operations structured names. A PDF text extractor, a language translator, an image classifier—each gets a URN that describes what it does. Systems can discover available capabilities and match requests to implementations.
The system has three parts:
- URN format - A structured way to name capabilities using key-value tags
- Matching algorithm - Rules for finding capabilities that satisfy a request
- Capability definitions - JSON schemas describing inputs, outputs, and behavior
URN Syntax
A capability URN starts with cap: followed by semicolon-separated key-value tags.
For the complete specification, see Tagged URN RULES.md.
Format
cap:key1=value1;key2=value2;key3=value3
Rules
- Prefix - Must start with
cap: - Tags - Key-value pairs separated by semicolons
- Keys - Lowercase alphanumeric with underscores and hyphens
- Values - Alphanumeric, underscores, hyphens, dots, slashes
- Case - Normalized to lowercase for comparison
- Order - Tags sorted alphabetically in canonical form
Examples
cap:op=extract;format=pdf;target=text cap:op=translate;language=es cap:op=classify;image;model=resnet
Quoting
Values containing special characters must be quoted:
cap:query="SELECT * FROM docs";format=json cap:path="/usr/local/bin";executable
Special characters requiring quotes: ; = " \ and uppercase letters.
Special Values
Tags support special pattern values for flexible matching:
| Value | Meaning | Example |
|---|---|---|
K=v | Must have key K with exact value v | format=pdf |
K=* | Must have key K with any value | format=* |
K=! | Must NOT have key K | debug=! |
K=? | No constraint on key K | format=? |
| (missing) | No constraint (same as ?) |
Value-less tags like optimize mean must-have-any (optimize=*).
Matching Algorithm
Matching determines if a capability can handle a request using per-tag semantics.
Per-Tag Truth Table
| Pattern | Instance Missing | Instance=v | Instance=x≠v |
|---|---|---|---|
(missing) or ? | OK | OK | OK |
K=! | OK | NO | NO |
K=* | NO | OK | OK |
K=v | NO | OK | NO |
Examples
# Capability: cap:op=extract;format=pdf;target=text # These requests match: cap:op=extract # no constraint on format/target cap:op=extract;format=pdf # exact match on format cap:op=extract;format=* # cap has format, request wants any # These do not match: cap:op=extract;format=docx # format mismatch (pdf ≠ docx) cap:op=extract;debug=* # request requires debug, cap lacks it cap:op=generate # op mismatch
Match function
In pseudocode:
function matches(instance, pattern):
for each key in union(instance.keys, pattern.keys):
inst = instance[key] // undefined if missing
patt = pattern[key] // undefined if missing
if patt is undefined or patt == "?":
continue // no constraint
if patt == "!":
if inst is defined: return false // must be absent
else if patt == "*":
if inst is undefined: return false // must be present
else:
if inst is undefined: return false
if inst != "*" and inst != patt: return false
return true
Specificity
When multiple capabilities match a request, the most specific one wins.
Graded Scoring
Specificity uses graded scores per tag:
| Value Type | Score |
|---|---|
Exact value (K=v) | 3 |
Must-have-any (K=*) | 2 |
Must-not-have (K=!) | 1 |
Unspecified (K=? or missing) | 0 |
Total specificity = sum of all tag scores.
# Request: cap:op=translate;language=es # Matching capabilities: cap:op=translate # specificity: 3 cap:op=translate;language=es # specificity: 6 (selected) cap:op=translate;language=* # specificity: 5 # The second capability wins with highest specificity.
Tie-breaking
If scores are equal, compare tuples (exact_count, must_have_any_count, must_not_count). If still tied, first registered wins.
Capability Definitions
A capability definition is JSON that describes what a capability does, what inputs it accepts, and what output it produces.
Structure
{
"urn": "cap:op=extract;format=pdf;target=text",
"title": "PDF Text Extractor",
"description": "Extracts text content from PDF documents",
"arguments": {
"required": [
{
"name": "input",
"type": "file",
"description": "PDF file to process"
}
],
"optional": [
{
"name": "pages",
"type": "string",
"description": "Index Range (e.g., '1-5' or '1,3,5')"
}
]
},
"output": {
"type": "text",
"description": "Extracted text content"
}
}
Argument types
string- Text inputnumber- Numeric inputboolean- True/falsefile- File path or binary datajson- Structured JSON object
Output types
text- Plain textjson- Structured JSONbinary- Binary data (images, files)
Libraries
CAPNS has implementations in four languages. All produce identical results following the same parsing and matching rules.
Rust (reference implementation)
github.com/filegrind/capns (built on tagged-urn-rs)
# Cargo.toml [dependencies] capns = "0.1"
use capns::{CapUrn, CapUrnBuilder};
// Parse a URN
let urn = CapUrn::parse("cap:op=extract;format=pdf")?;
println!("{}", urn.get_tag("action")); // "extract"
// Build a URN
let urn = CapUrnBuilder::new()
.tag("action", "translate")
.tag("language", "es")
.build()?;
// Match capabilities
if request.matches(&capability) {
println!("Matched with specificity: {}", request.specificity(&capability));
}
Go
github.com/filegrind/capns-go (built on tagged-urn-go)
import "github.com/filegrind/capns-go"
// Parse a URN
urn, err := capns.Parse("cap:op=extract;format=pdf")
if err != nil {
log.Fatal(err)
}
fmt.Println(urn.GetTag("action")) // "extract"
// Match capabilities
if request.Matches(capability) {
fmt.Printf("Matched with specificity: %d\n", request.Specificity(capability))
}
JavaScript
github.com/filegrind/capns-js (built on tagged-urn-js)
import { CapUrn, CapUrnBuilder } from 'capns';
// Parse a URN
const urn = CapUrn.parse('cap:op=extract;format=pdf');
console.log(urn.getTag('action')); // 'extract'
// Build a URN
const urn = new CapUrnBuilder()
.tag('action', 'translate')
.tag('language', 'es')
.build();
// Match capabilities
if (request.matches(capability)) {
console.log(`Matched with specificity: ${request.specificity(capability)}`);
}
Objective-C / Swift
github.com/filegrind/capns-objc (built on tagged-urn-objc)
// Swift usage via Objective-C bridge
import CAPNSObjC
// Parse a URN
let urn = try CapUrn.parse("cap:op=extract;format=pdf")
print(urn.getTag("action")) // "extract"
// Match capabilities
if request.matches(capability) {
print("Matched with specificity: \(request.specificity(capability))")
}
API Reference
The registry provides a REST API for querying and managing capabilities.
/cap:{tags}
Look up a capability by URN.
Example
GET /cap:op=extract;format=pdf
Response:
{
"urn": "cap:op=extract;format=pdf;target=text",
"title": "PDF Text Extractor",
"description": "Extracts text from PDF documents",
...
}
/api/capabilities
List all registered capabilities.
Response
[
{
"urn": "cap:op=extract;format=pdf;target=text",
"title": "PDF Text Extractor"
},
{
"urn": "cap:op=translate;language=es",
"title": "Spanish Translator"
},
...
]
/api/capabilities/match?q={urn}
Find capabilities matching a request URN, ordered by specificity.
Example
GET /api/capabilities/match?q=cap:op=extract
Response:
[
{
"urn": "cap:op=extract;format=pdf;target=text",
"specificity": 1
},
{
"urn": "cap:op=extract;format=epub;target=text",
"specificity": 1
}
]
/api/admin/capabilities
Register a new capability (requires authentication).
Request
POST /api/admin/capabilities
Authorization: Bearer {token}
Content-Type: application/json
{
"urn": "cap:op=summarize;format=text",
"title": "Text Summarizer",
"description": "Generates summaries of text content",
"arguments": { ... },
"output": { ... }
}