We built a programming language and runtime for AIs, not humans
For the first time in the history of computing, humans are no longer writing every line of code that runs in production. In a lot of cases, nobody will ever even read it. Every programming language ever built assumed a human was in the loop at least once. Qosm does not make that assumption.
It's a programming language and runtime designed to be read, written, and reasoned about by LLMs. To our knowledge, it's the first language built with that as an explicit goal.
A first taste
Here's a Qosm program. The host provisions two capabilities, http_get and db_insert, and the agent code calls them like any other function:
extern http_get : {url: String} -> String ! {Http.Get};
extern db_insert : {key: String, value: String} -> Unit ! {Db.Insert};let fetch_and_store url key =
let data = http_get {url: url};
db_insert {key: key, value: data};
// The agent can only call http_get and db_insert.
// No file access. No LLM. Nothing else exists.The host decides what to expose. The agent can only call what it receives. No file access, no environment variables, no network calls to arbitrary hosts. The capability list is the agent's entire footprint, checked at compile time.
Credentials don't belong in the code
In a conventional agent framework, the agent reaches for its own API key:
import anthropic, os
client = anthropic.Anthropic(api_key=os.environ["ANTHROPIC_API_KEY"])
response = client.messages.create(
model="claude-opus-4-5",
max_tokens=1024,
messages=[{"role": "user", "content": prompt}]
)
The key is in an environment variable, readable by any code in the process. If a prompt injection tricks the agent into calling a different endpoint or exfiltrating os.environ, nothing stops it. The security boundary is a naming convention.
In Qosm, the API key lives in the host. It provisions model before the agent code runs. The agent calls a typed function and can never see or forward the credential. It doesn't exist in the agent's scope.
Capabilities are functions
That's the core idea. Since a capability is a function, you can narrow it before handing it to an agent:
extern read_file : {path: String} -> String ! {File.Read};// Attenuate: restrict to a single directory.
let config_read path = read_file {path: "/config/" ++ path};
// Attenuate further: a single file, no arguments.
let app_config _ = read_file {path: "/config/app.toml"};
// The agent receives app_config.
// It cannot read anything else. Not by cleverness,
// not by prompt injection — by construction.The host doesn't just decide which capabilities to grant. It can scope them down before handing them off. No policy engine, no middleware. Just closures.
When capabilities compose, the types say so
extern db_insert : {key: String, value: String} -> Unit ! {Db.Insert};let classify text =
model @{category: String, confidence: Float}
`Classify this text: {{ text }}`;
let store label data =
db_insert {key: label, value: toString data};
let classify_and_store text =
match classify text with (
| Ok r -> store (.category r) r
| Err e -> store "error" e);
// Uses two capabilities: model and db_insert.
// The type tracks both. No surprises.classify_and_store has type String -> Unit ! {LLM.Call, Db.Insert}. The effect set is the full capability footprint of the program. The host can read it before anything runs. When capabilities compose, their effects merge. Nothing is hidden.
MCP tools become typed functions automatically
Connect a GitHub or Slack MCP server and every tool gets a generated typed signature:
// Auto-generated from connected MCP servers
extern create_issue : {repo: String, title: String, body: String}
-> {number: Int, url: String} ! {GitHub};
extern search_repos : {query: String, limit: Int}
-> Array<{name: String, stars: Int, url: String}> ! {GitHub};
extern send_message : {channel: String, text: String}
-> {ts: String} ! {Slack};
extern query : {sql: String, params: Array<String>}
-> Array<{row: {col: String, val: String}}> ! {PostgreSQL};
extern create_charge : {amount: Int, currency: String, customer: String}
-> {id: String, status: String} ! {Stripe};
extern web_search : {query: String}
-> Array<{title: String, url: String, snippet: String}> ! {Linkup};If the agent tries to call something that wasn't granted, or passes the wrong argument shape, the compiler rejects it. The effect annotations propagate through the whole program. If your function calls create_issue, its type says so.
Built to be written by models
Qosm is not an IDE. You write it with Claude Code, Codex, Cursor, or whatever you already use. The language is small by design. It takes less than 1k tokens to teach a model how to write valid Qosm. The type system catches mistakes before they run.
Agents are already writing production code. The question is whether we have the right tools to trust it. Type systems, effect tracking, and capability boundaries are not new ideas. Applying them to a world where the author is a model is.
Qosm is live in private beta. If you want to be an early customer, reach out to Pierre on LinkedIn.