> ## Documentation Index
> Fetch the complete documentation index at: https://usefused.com/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Project configuration

> Configure the agent, framework, server, discovery metadata, and dependencies.

Keep project and server settings together in `config.yaml`. The Agent Card owns public identity, and `pyproject.toml` owns dependencies.

| File                                            | Owns                                                            |     Commit it? |
| ----------------------------------------------- | --------------------------------------------------------------- | -------------: |
| `config.yaml`                                   | Framework, runtime environment, and optional `server` overrides |            Yes |
| `harnest-deployment.yaml`                       | Deployment workloads, services, resource limits, and replicas   | When deploying |
| `agent-card.yaml`                               | Public agent identity and capabilities                          |            Yes |
| `pyproject.toml`                                | Agent-owned Python dependencies                                 |            Yes |
| `harnest-runtime.lock`                          | Hash-verified production compilation resolution                 |            Yes |
| `harnest-development.lock`, `harnest-eval.lock` | Optional development/eval resolutions                           |      When used |
| `harnest.lock`                                  | Project schema and resolved framework version                   |            Yes |
| `.harnest/`                                     | Generated environments and artifacts                            |             No |

## Fix folder validation errors

Managed feature folders are configuration, not general storage. Harnest checks the files it finds there so that a misplaced file or unfinished declaration does not silently disappear from your agent.

Messages for misplaced files and missing declarations name the problem file, then explain **What Harnest expects** and **How to fix** it. Keep an active feature in its required format. For a note, backup, or unused example in a discovery folder, add `_` to the filename or move it outside that folder.

| Problem                                              | Repair                                                                                                                                                                                    |
| ---------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `sandbox/notes.txt` is treated as a sandbox resource | Rename the note to `_notes.txt` or move it elsewhere. Put each active sandbox in `sandbox/<name>.py`, define a matching variable, and assign the name with `Agent(sandboxes=["<name>"])`. |
| `tools/search.py` “must export 'search'”             | Define the intended tool as a top-level function or variable named `search`. “Export” means the named Python declaration Harnest looks for, not another file.                             |
| A skill folder has no `SKILL.md`                     | Create the skill's instruction file with that exact uppercase filename.                                                                                                                   |
| A Python file is named `search-customer.py`          | Use a Python-compatible name such as `search_customer.py`, then update its matching declaration and imports.                                                                              |

An underscore prefix leaves an unused entry out of automatic feature discovery; it does not repair or activate its code. Follow each generated example's destination and declaration instructions when enabling it. Put reusable Python helpers in `lib/`. The importable `lib/` and `models/` namespaces are different from feature discovery: underscore-prefixed Python modules can still be imported. Links to files or folders are still subject to Harnest's symlink restrictions.

See [generated examples](/docs/harnest/get-started/initialize) and [Sandboxing](/docs/harnest/build/sandboxing) for feature setup.

## `config.yaml`

`config.yaml` selects the entrypoint, framework, authoring mode, Python runtime, environment, secret references, and permissions. `harnest init` never generates `spec.resources` or `spec.scaling`; existing blocks are silently ignored:

```yaml theme={null}
apiVersion: harnest.dev/v1alpha1
kind: Agent
metadata:
  name: support-agent
spec:
  entrypoint: agent:root_agent
  framework:
    name: adk
    mode: managed
  interfaces:
    cli: true
```

Use `adk` or `langgraph`. Managed mode is the portable default; advanced mode accepts a native framework target. See [ADK and LangGraph](/docs/harnest/runtime/adk-and-langgraph). Unknown fields and invalid deployment values fail before authored Python loads.

`interfaces.cli: true` explicitly enables `harnest run` and the compiled
launcher's `run` command. Omit it for a server-only artifact.

Configure workload CPU and memory under `resources`, and instance counts under `replicas`, in [`harnest-deployment.yaml`](/docs/harnest/runtime/serving/provisioning). Existing `spec.resources` and `spec.scaling` blocks have no effect. Harnest silently ignores their contents, including empty, null, or invalid values, and leaves the source file unchanged. The standalone development server does not provision infrastructure, inject secret declarations, scale replicas, or enforce network permissions.

<Card title="Configure a model" icon="microchip" href="/docs/harnest/build/models-and-libraries/configure-a-model">
  Choose the model and endpoint, supply local or deployment credentials, and configure eval model reuse.
</Card>

## Retired resource and scaling fields

You can remove these ignored blocks from `spec` when cleaning up an existing project. Configure any limits you need explicitly:

| Removed setting                              | Where to configure it                                                                                    |
| -------------------------------------------- | -------------------------------------------------------------------------------------------------------- |
| `resources.cpu`, `resources.memory`          | Workload `resources.cpus` and `resources.memory` in `harnest-deployment.yaml`                            |
| `resources.timeoutSeconds`                   | Root `server.http.requestTimeoutSeconds` in `config.yaml`                                                |
| `resources.maxConcurrentRequests`            | Root `server.http.maxConcurrentRequests` in `config.yaml`                                                |
| `scaling.minReplicas`, `scaling.maxReplicas` | Workload `replicas` for a fixed instance count; configure autoscaling through your deployment platform   |
| `resources.ephemeralStorage`                 | Scratch-storage policy in your container or Kubernetes deployment; no replacement in agent `config.yaml` |

The old timeout and concurrency hints did not override standalone server settings. Review the behavior you want instead of copying every old value. Omit HTTP settings that match the defaults. These ignored blocks do not block `harnest upgrade` and do not supply defaults to Studio deployment discovery.

## Server settings in `config.yaml`

The optional root `server:` section controls the standalone bind, remote-bind consent, request timeout, concurrency, request-size limit, and playground. Omit the section to use all defaults, or specify only what you want to change:

```yaml config.yaml theme={null}
# Alongside apiVersion, kind, metadata, and spec:
server:
  live: true
  http:
    port: 9090
```

This example enables WebSockets on the HTTP listener and changes its port. Omit `live` for HTTP/SSE only. Exact `${NAME}` values are resolved and type-checked at startup. Authentication, persistence, TLS, secrets, and scaling do not belong in this section. Set explicit HTTP limits with `server.http.requestTimeoutSeconds` and `server.http.maxConcurrentRequests`; omit settings that match the defaults. See [Server configuration](/docs/harnest/runtime/serving/server-configuration) for defaults and legacy `server.yaml` migration.

## `agent-card.yaml`

The Agent Card supplies public discovery metadata and declared capabilities. Compilation validates and copies it into the artifact. The server exposes the card at `/.well-known/agent-card.json` and includes its identity and route links in `GET /agent`. Declare an A2A interface here when you want to [serve the agent through A2A](/docs/harnest/runtime/a2a/serve).

## `pyproject.toml` and `harnest-runtime.lock`

Declare only agent-owned provider, tool, and ordinary Python dependencies in `pyproject.toml`. Do not declare Harnest, ADK, LangGraph, LangChain adapters, or other Harnest-owned framework packages. Each Harnest release supplies and checks a compatible framework version.

Synchronize the project environment and commit the resulting lock:

```bash theme={null}
harnest env sync AGENT_DIR
```

The default `runtime` profile resolves the embedded release wheel, selected
framework, project and Harnest Extension dependencies, optional task runtime,
and every transitive dependency into `harnest-runtime.lock`. Every distribution
is hash verified. It does not install evaluation packages. ADK or LangGraph MCP
adapters join the solve only when an active `mcp/*.py` exists in the agent tree.

Development tools use independent profiles and locks:

```bash theme={null}
harnest env sync AGENT_DIR --profile development
harnest env sync AGENT_DIR --profile eval
```

The development profile adds pytest and writes `harnest-development.lock`. The eval profile
adds pytest plus Google ADK's evaluation dependencies and writes
`harnest-eval.lock`. `harnest serve`, `harnest run`, and ordinary `harnest test`
share development; `harnest test --evals` selects eval. Commit each lock used by CI. Development/eval locks are not
copied into deployable artifacts and do not change the deployable source digest.
The generated lock replaces machine-local wheel paths with a release marker, so
it can be reviewed and committed without recording a developer's filesystem.

The environment lives under `AGENT_DIR/.harnest/environments/` and should not
be activated. An explicit sync creates or updates `AGENT_DIR/.venv` as an
IDE-detectable link to the current environment. Harnest preserves an existing
`.venv` that it does not own and prints the exact managed interpreter instead.
`compile` selects the lean production runtime; `run`, `serve`, and ordinary
`test` select development; `test --evals` selects eval.
Each command synchronizes its internal environment automatically without
changing the IDE link and leases the selected
environment for its complete lifetime. After a replacement is published,
Harnest removes older unleased fingerprints asynchronously; overlapping tests,
compiles, and servers retain their environment until they finish. CI can
require a current committed lock without resolving or changing it:

```bash theme={null}
harnest env sync AGENT_DIR --frozen
harnest env sync AGENT_DIR --profile development --frozen
harnest env sync AGENT_DIR --profile eval --frozen
```

## `harnest.lock`

`harnest.lock` records the project schema and the exact framework distribution installed by `harnest env sync`. A new scaffold starts with the schema only; synchronization adds the resolved version:

```yaml harnest.lock theme={null}
apiVersion: harnest.dev/v1alpha1
kind: ProjectLock
projectSchema: 5
framework:
  name: langgraph
  distribution: langgraph
  version: 1.2.11
```

Commit this file alongside the profile locks used by the project. Later environment syncs install the exact resolution, and compilation rejects a different installed framework version before loading agent code. A frozen profile sync requires matching framework and profile locks and leaves them unchanged. It rejects changed dependency inputs before installation.

To deliberately resolve a newer supported framework release, remove only the `framework` entry and run environment sync again, then review and commit the new pin. Changing the selected framework in `config.yaml` followed by normal sync records the new framework; frozen sync rejects that change. Project schema migrations use `harnest upgrade` and preserve the framework pin.

Harnest's CI exercises both framework adapters and the shared evaluation engine against pinned, minimum-supported, and latest-compatible dependencies on Python 3.11 and 3.12, on pull requests and daily. `harnest.lock` records the selected framework; `harnest-runtime.lock` remains the lean deployment resolution, while development and eval tooling stays in its own locks.
