1
0
Fork 0
Code Issues Pull requests Projects Releases 2 Packages Wiki Activity Actions Pages
DocForge2/docs/CONTRACT.md
2026-08-02 20:52:36 -04:00

443 lines
30 KiB
Markdown

# DocForge 2.0 contract
## Authority boundary
DocForge is bound to one explicit project root. Canonical project files own documentation facts.
Indexes, query results, context packs, changesets, previews, and renders are derived artifacts.
The generic core validates and retrieves canonical nodes. A project-bound proposal service writes
isolated changesets. A separately gated canonical application service may apply one exact,
hash-approved changeset through a generic or project-owned serializer. Project builds, Git mutation,
deployment, and publication remain external. Passive revision detection may read the current Git
commit when Git is available; it cannot change repository state.
## Versioned contracts
- Project descriptor schema: `schemas/project.schema.json`, version 1.
- Node schema: `schemas/node.schema.json`, version 1.
- Edge schema: `schemas/edge.schema.json`, version 1.
- Result envelope: `schemas/result.schema.json`, version 1.
- Changeset schema: `schemas/changeset.schema.json`, version 1.
- Effective policy: `schemas/policy.schema.json`, version 1.
- Task context capsule: `schemas/context-capsule.schema.json`, version 1.
- Latest generation diff: `schemas/generation-diff.schema.json`, version 1.
- Latest generation-diff page: `schemas/generation-diff-page.schema.json`, version 1.
- Generated client configuration: `schemas/client-configuration.schema.json`, version 1.
- Client doctor result: `schemas/doctor-result.schema.json`, version 1.
- Manual render plan: `schemas/manual-render-plan.schema.json`, version 1.
- Graph view plan: `schemas/graph-view-plan.schema.json`, version 1.
- Projection package: `schemas/projection-package.schema.json`, version 1.
- Projection receipt: `schemas/projection-receipt.schema.json`, version 1.
- Independent projection policy: `schemas/projection-policy.schema.json`, version 2.
- Adapter launcher: `schemas/adapter-launcher.schema.json`, version 1.
- Adapter client configuration: `schemas/adapter-client-configuration.schema.json`, version 1.
- Reference adapter configuration: `schemas/reference-adapter.schema.json`, version 1.
- Index schema: version 3, disposable and reproducible.
- Index attestation: schema version 1, disposable and reproducible.
- Distribution, Python package, CLI, generic MCP, reference MCP, and viewer manager: version 2.0.0.
- Incremental extraction cache: version 1, disposable and reproducible.
Schema files describe the generic interchange contract. Runtime validation remains responsible for
path confinement, source hashing, relationship resolution, dependency cycles, project limits, stale
state, and adapter-specific rules that JSON Schema cannot prove by itself.
`src/docforge/_version.py` is the sole package-version authority. The maintained executable
surfaces report exactly `docforge 2.0.0`, `docforge-mcp 2.0.0`,
`python -m docforge.reference_mcp 2.0.0`, and `docforge-viewer-manager 2.0.0` for `--version`.
Generated generic and adapter client configurations bind `docforge_version` into their validated
hashes.
## Generic node storage
Markdown nodes begin with a TOML metadata block delimited by `+++`. The remaining Markdown is the
node content. TOML sources contain one or more `[[nodes]]` tables and store content in a `content`
field. Every node has a stable project-wide ID.
The generic authority vocabulary is `authoritative`, `approved_plan`, `derived`, `proposal`, and
`historical`. Projects define statuses and allowed relationship names in their descriptor. The core
gives special acyclic validation to `depends_on`; adapters may add stricter rules.
## Result identity
Successful operations identify the project, adapter, current revision when available, and canonical
source hash. Errors use a stable code, direct message, structured details, and a bounded remediation
tool when recovery is safe. MCP operations synchronize disposable index state under a project lock
before reading or proposing. Canonical source validation remains fail-closed.
Task-context retrieval derives a closed version-1 plan from a bounded task kind and the effective
process policy. It executes against one immutable index transaction and returns generation-bound,
hash-identified evidence, gaps, omissions, and provenance limitations. Project relation names
remain authoritative. The core applies task semantics only to its versioned alias set and preserves
every other allowed relation as unclassified.
An atomic index build writes a whole-file SHA-256 attestation after complete graph, row, FTS, and
SQLite integrity verification. A fresh process may use that receipt to verify an unchanged index
without reconstructing all graph rows. A missing, malformed, or mismatched receipt falls back to
complete verification and is repaired only after that verification succeeds.
Index replacement is the derived publication commit point. Attestation, cheap source-generation,
and latest-generation-diff receipts are independent post-commit evidence. Their failure produces
bounded degraded success and never falsely reports that a committed index mutation failed.
Derived publication stages and flushes one complete bounded artifact before atomic replacement or
no-clobber publication, then flushes the containing directory. An interruption therefore leaves
the preceding complete artifact, the new complete artifact, or explicit degraded post-commit
evidence. Index attestations, manual render receipts, generation-diff baselines, and portable-graph
manifests have maintained exact-oracle corruption-and-repair proofs. Canonical project files remain
unchanged throughout those recoveries.
Before replacement, a build accepts a predecessor only when its exact main-file inode has a
matching whole-file attestation, has no WAL, journal, or shared-memory sidecar, and passes the
published SQLite identity, row, hash, FTS, integrity, and policy checks. It uses an immutable
main-file read and never repairs predecessor evidence. The build then revalidates the new source
snapshot including exact node and edge equality and rejects a stable source identity that produces
different graph content as `generation_collision`.
The version-1 generation-diff receipt stores one bounded latest primary-graph transition. It is
not history and contains no Logic details or source text. Public pages carry one
`receipt_header`; its `stored_receipt_hash` identifies the complete persisted receipt rather than
the header alone. One top-level pagination object carries the only continuation cursor.
## Machine-local client integration
Generated Codex, Claude, and OpenClaw fragments are machine-local projections. They are not
canonical project content. Version 1 binds the selected project, exact isolated Python
interpreter, canonical argument layout, effective policy, no-AST projection, render policy,
timeouts, artifact bytes, and configuration hash. Milestone 3 adds the version-2 projection policy,
its hash, projection availability, and the exact descriptor hash to that attested configuration
evidence. Omitted default selectors are recomposed against the bound descriptor.
Preview is side-effect free. Explicit publication creates only one new private standalone
fragment in an existing real directory. It never merges or replaces different content. Descriptor,
parent, target, content, ownership, permission, and link identities are checked before and after
the directory durability boundary. A failure rolls back when that can be proven and otherwise
returns bounded unconfirmed publication evidence.
Doctor is a bounded read-only inspector with one fixed check inventory. It uses stable no-follow
descriptor and configuration reads plus stat-only derived-index evidence. It never loads a
complete projection, opens SQLite, starts MCP, executes the configured command, synchronizes,
builds, renders, starts a viewer, or writes configuration. Unprovable client behavior is a warning,
not an invented success.
## Public adapter SDK and reference binding
`docforge.adapter_sdk` is the stable adapter-authoring import boundary. It exposes the typed
projection, manifest, source contribution, complete assembly, project wrapper, graph model, and
conformance contracts needed by an adapter without requiring authors to import core implementation
modules.
Complete evidence includes the primary graph and function Logic. An incremental adapter that
publishes Logic must implement `load_complete_assembly()` as an independent complete oracle.
`verify_adapter_conformance()` proves repeated complete determinism, equality between the complete
assembly and `load_projection()`, and exact complete/incremental graph-plus-Logic parity. Separate
tests remain responsible for confinement, restart behavior, no-AST behavior, cache recovery, and
retrieval.
Adapter assemblies are bounded before publication. Primary nodes use the descriptor `max_nodes`
limit. Primary edges, Logic nodes, and Logic edges use fixed deterministic multipliers over that
limit. Version-1 extraction caches are regular-file-only, bounded to 10,000 sources and
64,000,000 bytes, and are treated as misses when corrupt, oversized, foreign, or incompatible.
`.docforge/reference-adapter.toml` is a closed version-1 selection among `python`, `javascript`,
`typescript`, and `cpp`. It declares one project identity and explicit non-overlapping source
roots. C++ additionally requires a confined `compile_commands.json`. It cannot declare a command,
module, environment, writer, applier, or remote endpoint.
`python -m docforge.reference_mcp --project-root ROOT` constructs only the selected fixed
repository reference adapter and exposes the read surface. It never registers proposal or
application tools.
`AdapterLauncherV1` is an immutable project-bound Python-module declaration. It accepts no
arbitrary command, arguments, working directory, environment, discovery, callable selector, or
module reload. Custom launchers resolve one installed top-level module through isolated Python and
require its origin inside the project root. The fixed `docforge.reference_mcp` module is the only
trusted dotted exception. `generate_adapter_client_configuration()` binds generated Codex,
Claude, and OpenClaw fragments to that launcher, current source availability, effective policy,
descriptor, interpreter, and exact artifact bytes.
## Isolated proposal model
Create, update, move, and delete are ordered node operations inside an isolated changeset. Every
operation names its expected base hash. A move preserves the stable node ID. A delete must resolve
every incident relationship. Proposal validation and storage are atomic. Application requires the
exact final changeset hash; prose is never auto-merged.
Relationship-only additions and removals use the validated update operation without changing node
metadata or content. They remain bound to the complete changeset base hash and the anchor node's
expected content hash.
The MCP process binds to one configured writer identity at startup. The project descriptor grants
that writer explicit families and operation types. A changeset records its creator, project root
fingerprint, base revision, canonical source hash, and ordered operations. Every append requires the
current changeset hash, so simultaneous writers cannot silently lose an operation.
The atomic registration operation captures a complete operation list against one current base,
fills omitted existing-node hashes from that synchronized snapshot, validates once, and writes one
final changeset.
Changesets from the same canonical base may coexist only when their touched node and source sets do
not overlap. Exact overlaps return structured conflicts naming the other changesets, nodes, and
sources. A stale canonical base, stale node hash, stale changeset hash, unauthorized family, unsafe
path, invalid graph, dependency cycle, unresolved delete relationship, or configured limit fails
before the proposal file changes.
A stale proposal may be rebased only when its stored node hashes, source targets, relationship
preconditions, permissions, conflict set, and complete projected graph still validate against the
current project. Application and explicit abandonment create derived lifecycle receipts. The
default active listing contains only draft and ready work. Stale, applied, and abandoned proposals
remain queryable by explicit status or history request. Terminal proposals do not block new
proposals.
## Canonical application durability
Generic canonical application stages replacements and backups in a mode-0700
`.docforge/application/transaction-*` directory. Before each canonical create, update, or delete,
it compares exact file identity at the publication boundary. Creates use no-clobber publication.
Updates and deletes use atomic exchange and no-replace detachment. A concurrent canonical-target
mutation fails closed, is rolled back only when exact displaced state remains provable, or is
retained without overwriting foreign data.
This is per-file compare-and-swap publication, not multi-file crash atomicity. In-process failures
run rollback across already published files, but there is no process-death journal. Process or host
death between publications may leave a partial canonical application and requires operator
inspection before a new proposal or restoration.
The private transaction namespace is integrity-confined against ordinary path access. It is not a
filesystem sandbox, and deliberate arbitrary tampering by another process with the same operating-
system UID is outside the contract. DocForge identity-checks private files before consuming or
removing them.
After the serializer reproduces the approved graph, canonical success is final. If private cleanup
then degrades, application still returns `applied`, closes the proposal, and persists bounded
`application_recovery` lifecycle metadata with status `cleanup_required`, retained paths, and
remediation. The reviewed changeset must not be applied twice.
## Declared rendering and previews
Render configuration is optional. A configured project declares one template root, one isolated
preview root, and one or more stable view IDs. Each view names a built-in renderer, template,
derived output file, title, and optional family filter. Paths are resolved under the project root
and may not overlap canonical content, authority files, changesets, templates, or previews.
The `generic_html` renderer uses pinned CommonMark parsing with raw HTML disabled. Templates are
UTF-8 files with a fixed token vocabulary; they cannot name commands, modules, or executable
renderers. Render identity covers the canonical source hash, optional changeset hash, selected node
and edge identities, view configuration, template hash, renderer contract, and exact parser
version. The frozen version-1 API and alpha bytes are preserved by a compatibility wrapper over the
manual plan/package/renderer path.
An explicit CLI render atomically replaces one declared derived output. MCP can render a validated
changeset only to its isolated preview path. Normal status verifies bounded source, configuration,
template, output, renderer, and publication-receipt identities without reconstructing the output.
Explicit deep status remains the side-effect-free full-render oracle. Input changes detected before
atomic replacement fail without publishing a current receipt for stale output.
## Independent projection boundary
Manual and portable graph plans are separate version-1 contracts over one immutable validated
generation. They use canonical JSON, deterministic ordering, fixed structural and serialized-size
bounds, and content-derived identities. Plans contain selected graph facts and bounded content.
They contain no live project object, database handle, absolute project or index path, arbitrary
query, command, executable path, or caller-selected module.
Projection packages bind one plan to inert assets, a closed built-in renderer identity, declared
component versions, and an artifact inventory with a byte allowance. Receipts bind the exact
package, plan, renderer, artifact hashes and sizes, diagnostics, timing, and detached peak memory.
Manual and graph renderer modules accept only validated packages. They cannot select nodes, invent
relationships, read project state, choose publication paths, or write canonical files.
Detached execution uses one fixed private Python module, isolated mode, a trusted working
directory, a sanitized environment, exactly one canonical newline-terminated JSON request and
response, a closed renderer allowlist, a 30-second timeout, disk-spooled stdout, and bounded reads. The package
contract is capped at 24,000,000 bytes and actual detached artifact transfer at 20,000,000 bytes.
Project descriptors may retain a larger `max_render_bytes` compatibility allowance, but an actual
detached transfer above the fixed worker boundary fails closed.
Portable graph configuration is independent of manual render configuration. One view selects
either an exact root or a bounded metadata-only lexical query plus closed filters and node, edge,
depth, and work limits. Logic is excluded. The renderer emits a complete static Nodes, Flow, or Web
artifact and uses JavaScript only as progressive enhancement.
Portable publication commits a content-addressed artifact, renderer receipt, and one bounded
generation/view manifest in that order. The manifest is the publication commit. Status reads only
bounded manifest and receipt evidence and never plans or renders. Repair restores declared output
only from validated content-addressed evidence. A failure after a replacement that cannot be
proven rolled back returns explicit degraded committed evidence.
Manual fragment records are disposable semantic cache entries. Their keys bind the renderer,
component version, and complete page semantics. The detached renderer recomputes the expected page
fragment before accepting cached bytes. Cold creation is compared with a full detached render
before cache publication. Invalid, corrupt, forged, stale, individually oversized, or
aggregate-oversized records fall back to the full oracle. The dedicated cache retains only current
keys and is capped at 10,000 entries and 64,000,000 bytes.
Projection policy version 2 composes manual `auto|explicit|disabled`, portable graph
`explicit|disabled`, and live viewer `on-demand|disabled` independently. Active plan, render,
application, onboarding, and viewer-start operations enforce the relevant policy before hidden
work. Receipt-only status and explicit viewer stop remain available. Effective policy version 1
and its legacy projections remain unchanged.
The live viewer remains separate from portable graph publication. It consumes one
generation-pinned validated index through the viewer manager. Source reads come from that pinned
generation and do not reopen mutable canonical files behind an older snapshot. Neither live nor
portable visualization is retrieval or canonical authority.
Normal MCP access does not expose canonical application. An explicitly configured canonical
applier registers one hash-bound application tool. No MCP mode exposes arbitrary renderer
execution, arbitrary file writes, shell commands, Git mutation, build commands, deployment, or
publication.
## Project-bound graph visualization
The fixed `docforge_visualize` MCP tool starts one persistent read-only graph browser for the
server's already-configured project. It accepts only an optional stable node ID, an optional lexical
query, and a bounded traversal depth. It does not accept a project root, database path, SQL,
template path, bind address, command, or renderer.
The runner validates the complete canonical projection and derived index before it starts. It then
pins the browser to that exact validated SQLite file identity and project metadata so normal UI
queries do not rebuild a large adapter graph. Replacement or alteration of the index file makes the
browser fail closed; the user must invoke the tool again. The browser identifies itself as a
validated snapshot rather than claiming that canonical files are continuously monitored.
The HTTP listener binds to `127.0.0.1` on an operating-system-selected port. A cryptographically
random token is part of every accepted URL path. Only `GET` and `HEAD` are supported. Responses use
no-store caching, a restrictive content-security policy, frame denial, MIME sniffing protection,
and no-referrer policy. The built-in template uses only same-origin JSON endpoints for graph
overview, bounded search, exact descriptor-category filtering, exact node content, bounded
incoming-and-outgoing neighborhoods, semantic Flow ancestry, convergence Web context, lazy
function-scoped Logic, and one node's bounded project-confined source file.
Descriptor filtering accepts only family, authority, status, or tag plus one exact value.
Search filtering accepts only family, indexed kind or callable, indexed language tag, and the
fixed `logic` or `source` capability. There is no write endpoint, arbitrary query endpoint, static
filesystem handler, external asset, or project-selection control.
The `graph-browser@17` template provides mouse-wheel zoom centered on the pointer, left-button drag
pan, explicit zoom-in and zoom-out buttons, a reset-view button, and a live zoom percentage. A
four-pixel drag threshold defers pointer capture and preserves node activation for ordinary clicks.
Loading another root node fits the viewport to the returned neighborhood, including a useful
minimum scale for a single-node result. The current root begins selected, and activating another
graph node moves the visible selection ring to it. Space centers the viewport on the selected node
without changing zoom. Reset restores the fitted neighborhood view. Empty-canvas guidance is hidden
whenever a neighborhood is rendered. The page is fixed to the browser viewport. Search and exact
filter results fill the left panel, neighborhood traversal fills the right panel, and only the
center SVG canvas pans or zooms.
Canvas nodes are semantic cards. The focus and relation-derived Structure, Behavior, Dependency,
Execution, Data, Evidence, Context, and Related categories have distinct rails and badges. Cards
display the readable leaf title and node kind. Long titles wrap instead of being clipped. The
complete qualified title and stable node identifier remain available in the SVG tooltip and node
inspectors. This display shortening is presentation-only and never changes indexed identity.
Left-clicking or pressing Enter on a graph node opens a compact descriptor card containing the
validated metadata and content previously shown in the details panel. Its family, authority,
status, and tag pills are buttons that replace the left result list with exact matching nodes.
The left result panel also exposes composable family, node-kind, language, and capability filters
plus fixed convenience presets. These filters are bounded read-only queries over indexed
attributes and stored Logic ownership. Selecting a canvas node emphasizes only its incident edges
and directly connected nodes; unrelated visible paths are muted but remain present.
Right-clicking or pressing Shift+Enter opens the complete inspector. Inspection does not replace
the current neighborhood or reset the viewport. Both dialogs support Escape, explicit close
controls, and backdrop dismissal. Loading the inspected node as the new root requires the separate
Explore neighborhood action. Non-focus nodes may be hidden from the presentation and restored
without mutating graph state. Flow and Web recompute focus reachability after each hide so
disconnected upstream-only branches are pruned while downstream convergence remains visible.
Source actions open the project-confined source and navigate to
supported line, TOML, heading, or text anchors. Both side panels support pointer and keyboard
resizing. The unblurred full inspector supports native resizing, constrained title-bar dragging,
and a fixed header/footer surrounding a scrollable body.
The header exposes a Nodes/Flow/Web/Logic segmented selector. Nodes displays the complete bounded
neighborhood. Flow displays semantic ancestry ending at the current root. Structural and execution
edges retain their declared source-to-target direction. Reads, imports, dependencies, inheritance,
and `tested_by` reverse because their declared target feeds or qualifies the source. Documentation
and context relations remain available in Nodes and Web but are excluded from Flow. Web follows
all relationship types as bounded semantic contributors into the current root. It also reverses
direct root-owned members and execution dependencies into adjacent contributor branches. Traversal
does not fan back out through unrelated siblings. These are presentation transforms over the
validated snapshot; they do not add or change project relationships.
Logic is available only when the focused node owns a stored `LogicProjection`. The browser
retrieves that projection through a bounded, exact-owner endpoint. Entry, condition, action,
control, convergence, return, raise, and exit nodes remain outside primary graph search and
traversal.
Logic edges retain their declared `TRUE`, `FALSE`, `NEXT`, `CASE`, `LOOP`, `EXCEPTION`, `RETURN`,
`RAISE`, `BREAK`, and `CONTINUE` labels. Hiding a logic node creates a visible omitted-path bridge
between retained predecessors and successors instead of pruning valid downstream control flow.
Nodes, Flow, and Web color edges by relationship semantics and retain direction with visible SVG endpoint
symbols. Line patterns provide a non-color cue. A static canvas key shows the exact symbol, color,
label, and visible count for each displayed relation, including a deterministic fallback for
project-defined relations. Logic uses a separate fixed control-flow map.
The browser derives node presentation roles only from the returned bounded graph. The current root
is the focus. In Nodes, nodes reachable through outgoing edges are shown as outgoing paths; the
remaining visible nodes are incoming or lateral context. In Flow, lineage predecessors are shown as
upstream nodes. In Web, all retained contributors share the convergence role. These roles receive
distinct palettes and navigation sections. An undirected shortest-hop calculation places Nodes on
distance rings; Flow and Web use left-to-right distance layers with the destination on the right.
Each role palette darkens progressively by distance, capped at fifty percent.
Logic uses a layered left-to-right layout with explicit horizontal clearance and vertical
separation between siblings. Control-flow edges use routed curves and distinct lanes, including
raised return and loop-back routes, to avoid drawing one path directly over another whenever the
bounded topology permits.
Each invocation creates or reuses one worker through the separately supervised, per-user viewer
manager. The manager is outside the short-lived MCP transport and owns all child workers as one OS
service unit. It accepts only authenticated loopback requests and a validated immutable snapshot.
A repeated invocation reuses its unguessable URL when the snapshot is unchanged. If the index has
changed, it replaces the worker only after a fresh complete index check.
`docforge_visualization_status` reports the managed worker state. `docforge_stop_visualization`
explicitly stops the current project's worker. The manager applies a one-hour activity timeout to
genuinely abandoned workers. Browser activity renews that timeout, but normal MCP transaction or
host-process completion does not affect it. The manager itself is restarted by an OS-native,
per-user supervisor. Project-specific integrations receive the same tools because the parent
validates and serializes only the supplied `ProjectService` and `ProjectIndex` snapshot; workers do
not discover projects or load canonical sources.
## Project adapter boundary
An adapter supplies one deterministically ordered `AdapterProjection` containing core nodes and
edges plus ordered adapter metadata. The core validates root identity, graph integrity, stable
ordering, and metadata-key uniqueness before exposing the projection through the standard derived
index. The loader is called again during an operation so identity or source changes fail closed.
Adapters own stricter project semantics such as authority precedence, phase rules, context
selection, query ordering, and render-model composition. They may not weaken root confinement,
canonical authority, graph validation, hashing, stale-state checks, or derived-output boundaries.
Shadow adapters are explicit local integrations and are not loaded by the normal generic MCP
process. A project integration may explicitly construct a read-only MCP server from one validated
`ProjectService` and an optional project-owned context provider. That server exposes only the fixed
read tool surface. The core does not discover adapters, choose projects or sessions, or import
project policy.
A proposal-enabled adapter declares confined canonical source, changeset, template, preview, and
render paths plus fixed writer permissions. It must supply a proposal validator. The core continues
to enforce optimistic hashes, writer permissions, graph integrity, limits, atomic changeset storage,
conflict detection, and preview confinement. The adapter validator enforces source-format and
project semantics that the generic core cannot infer. Generic projects retain the built-in Markdown
and TOML source-layout validator.
An explicit integration may construct the full fixed MCP surface for a configured adapter project
and one startup-bound writer. Canonical application is registered only when the integration also
supplies a startup-bound applier identity and project-owned `CanonicalApplier`. An adapter without
proposal settings or validation remains read-only.
An adapter may additionally implement the opt-in incremental contract. Its manifest inventories
stable source IDs, fingerprints, extractor versions, and source dependencies without parsing the
complete project. Each extraction owns deterministic nodes, relationships, and optional
function-scoped logic. Added, changed, deleted, and reverse-dependent sources are invalidated.
Cached and refreshed facts are always assembled into a complete projection and pass normal graph
validation before publication. The full projection loader remains the fallback and equivalence
oracle.
The Release 1 `AdapterLoader` contract remains valid. A loader that supplies only
`load_projection()` stays on the complete-projection path. Incremental capability detection is
additive and cannot make the new methods mandatory for an existing adapter. An incremental loader
must also implement `load_projection()` so a clean rebuild and equivalence check remain possible.
Logic projections are not primary graph nodes. They remain source-scoped, function-owned,
independently cached control-flow data so ordinary search, Nodes, Flow, and Web do not become
statement graphs. Index schema 2 stores them in dedicated owner, node, and edge tables. Reads are
bounded to one exact function or method owner.