# UKO — Unified Knowledge Ontology

This document describes the **Unified Knowledge Ontology (UKO)**, a layered
RDF/Turtle ontology used by CleverAgents to represent code artifacts,
structural relationships, and language-specific extensions.

## Overview

UKO organises knowledge into four layers, each building on the previous:

| Layer | Prefix(es) | IRI Namespace | Purpose |
|-------|------------|---------------|---------|
| 0 | `uko:` | `https://cleveragents.ai/ontology/uko#` | Universal foundation — base information unit types and core relationships |
| 1 | `uko-code:`, `uko-doc:`, `uko-data:`, `uko-infra:` | `https://cleveragents.ai/ontology/uko/code#` etc. | General software — modules, callables, types, tests, imports |
| 2 | `uko-oo:`, `uko-func:`, `uko-proc:` | `https://cleveragents.ai/ontology/uko/oo#` etc. | Paradigm-specific — OO classes, interfaces, methods, attributes |
| 3 | `uko-py:`, `uko-ts:`, `uko-rs:`, `uko-java:` | `https://cleveragents.ai/ontology/uko/py#` etc. | Technology-specific — DetailLevelMap insertions (no OWL classes) |

The ontology file lives at `docs/ontology/uko.ttl` and uses the base URI
`https://cleveragents.ai/ontology/uko#`.

## URI Format and Prefix Conventions

Every UKO concept is identified by a URI under the CleverAgents ontology
namespace.  Layers use semantic domain prefixes rather than numeric indices:

```
https://cleveragents.ai/ontology/uko#            # Layer 0 (foundation)
https://cleveragents.ai/ontology/uko/code#       # Layer 1 (code domain)
https://cleveragents.ai/ontology/uko/oo#         # Layer 2 (OO paradigm)
https://cleveragents.ai/ontology/uko/py#         # Layer 3 (Python — reserved)
```

In Turtle files these are abbreviated using `@prefix` declarations:

```turtle
@prefix uko:      <https://cleveragents.ai/ontology/uko#> .
@prefix uko-code: <https://cleveragents.ai/ontology/uko/code#> .
@prefix uko-oo:   <https://cleveragents.ai/ontology/uko/oo#> .
```

## Layer Descriptions

### Layer 0 — Universal Foundation (`uko:`)

Defines the root types that all other layers extend:

- **InformationUnit** — the root of every UKO node; anything that can appear in an actor's context.
- **Container** — an information unit that contains other units (file, module, class, section).
- **Atom** — a leaf-level information unit (function body, paragraph, config value).
- **Annotation** — metadata attached to another unit (comment, docstring, attribute).
- **Boundary** — an interface point between containers (export, API endpoint, public method signature).

Core relationship properties:

- **contains** — parent contains child (`rdfs:domain` Container, `rdfs:range` InformationUnit).
- **references** — weak reference (e.g. a function mentions a type in a docstring).
- **dependsOn** — strong dependency (import, inheritance, call).

Content properties:

- **hasRendering** — rendered text at a specific detail depth.
- **renderingDepth** — the integer detail depth of the associated rendering.
- **hasFullContent** — shorthand for the maximum-depth rendering.

Provenance properties:

- **sourceResource** — the CleverAgents Resource (by ULID) this node was extracted from.
- **sourcePath** — file path within the resource.
- **sourceRange** — byte or line range within the source file (e.g. `42:1-87:0`).

Temporal properties:

- **validFrom** — timestamp when this node version became valid.
- **validUntil** — timestamp when this node version was superseded.
- **isCurrent** — whether this is the current version.
- **isRevisionOf** — links a revised node to its predecessor.

### Layer 1 — General Software (`uko-code:`)

Structural code concepts that extend Layer 0 classes:

- **Module** — a source code module (subclass of Container).
- **Callable** — any callable unit: function, method, procedure, lambda (subclass of Atom).
- **TypeDefinition** — a type or schema definition (subclass of Atom).
- **TestCase** — a test case or test function (subclass of Atom).
- **Import** — an import/include/require statement (subclass of Annotation).

Layer 1 properties:

- **hasReturnType** — datatype property on Callable.
- **hasParameters** — JSON-encoded parameter list on Callable.
- **testsCallable** — links a TestCase to the Callable it tests.

### Layer 2 — Object-Oriented Paradigm (`uko-oo:`)

OO-specific specialisations of Layer 1 classes:

- **Class** — an OO class (subclass of TypeDefinition).
- **Interface** — an interface or abstract base class (subclass of TypeDefinition).
- **Method** — a method defined within a class (subclass of Callable).
- **Attribute** — a class or instance attribute (subclass of Atom).

Layer 2 properties:

- **inheritsFrom** — `rdfs:subPropertyOf uko:dependsOn`; domain/range both Class.
- **implements** — `rdfs:subPropertyOf uko:dependsOn`; domain Class, range Interface.

Note: `uko-oo:Class` has dual `rdfs:subClassOf` parents
(`uko-code:TypeDefinition` and `uko:Container`), and `uko-oo:Interface`
has dual parents (`uko-code:TypeDefinition` and `uko:Boundary`).  The
loader supports multi-parent `rdfs:subClassOf` and resolves inheritance
as a DAG using BFS.

### Layer 3 — Technology-Specific

Per the specification, Layer 3 is defined via DetailLevelMap insertions
rather than new OWL classes.  The `uko-py:` prefix is reserved for
Python-specific extensions when DetailLevelMap support is added.

## Versioning

The ontology carries an `owl:versionIRI` that encodes a semver string:

```turtle
uko: a owl:Ontology ;
    owl:versionIRI <https://cleveragents.ai/ontology/uko/0.1.0> .
```

The loader extracts the version from the last path segment of the IRI and
validates it against the `SUPPORTED_VERSIONS` registry.

## Extension Points

To add a custom domain or language binding:

1. Define a new `@prefix` (e.g. `uko-go:`) in `uko.ttl`.
2. Declare classes using `rdfs:subClassOf` to connect them to the
   appropriate parent in Layers 0-2.
3. Update the `_LAYER_PREFIXES` and `_LAYER_IRI_PREFIXES` maps in
   `uko_loader.py` so the parser assigns the correct layer number.
4. Add the new version string to `UKOLoader.SUPPORTED_VERSIONS`.

## Parsing Walkthrough

```python
from pathlib import Path
from cleveragents.application.services.uko_loader import UKOLoader

loader = UKOLoader()
ontology = loader.load(Path("docs/ontology/uko.ttl"))

# List Layer 0 nodes
for node in loader.get_layer_nodes(ontology, layer=0):
    print(node.label, node.uri)

# Resolve inheritance for uko-oo:Class
chain = loader.resolve_inheritance(
    ontology,
    "https://cleveragents.ai/ontology/uko/oo#Class",
)
for node in chain:
    print(f"  Layer {node.layer}: {node.label}")
```

Output:

```
InformationUnit https://cleveragents.ai/ontology/uko#InformationUnit
Container https://cleveragents.ai/ontology/uko#Container
Atom https://cleveragents.ai/ontology/uko#Atom
Annotation https://cleveragents.ai/ontology/uko#Annotation
Boundary https://cleveragents.ai/ontology/uko#Boundary
contains https://cleveragents.ai/ontology/uko#contains
references https://cleveragents.ai/ontology/uko#references
dependsOn https://cleveragents.ai/ontology/uko#dependsOn
hasRendering https://cleveragents.ai/ontology/uko#hasRendering
renderingDepth https://cleveragents.ai/ontology/uko#renderingDepth
hasFullContent https://cleveragents.ai/ontology/uko#hasFullContent
sourceResource https://cleveragents.ai/ontology/uko#sourceResource
sourcePath https://cleveragents.ai/ontology/uko#sourcePath
sourceRange https://cleveragents.ai/ontology/uko#sourceRange
validFrom https://cleveragents.ai/ontology/uko#validFrom
validUntil https://cleveragents.ai/ontology/uko#validUntil
isCurrent https://cleveragents.ai/ontology/uko#isCurrent
isRevisionOf https://cleveragents.ai/ontology/uko#isRevisionOf
  Layer 2: Class
  Layer 1: TypeDefinition
  Layer 0: Container
  Layer 0: Atom
  Layer 0: InformationUnit
```
