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

# Author a contract from scratch

> Build a complete acknowledgement template, validate it, and submit and sign it through the Agent API

Create a template with one participant and one text parameter. The complete example records an acknowledgement; its machine-readable instruction performs no payment or token creation.

The XML passes the documented local schema checks. Template approval and signing still need verification on your development service. Arrange that service access before running the submission steps.

## Prerequisites

* Complete [your first Agent API call](/neuron-api/first-request).
* Have an [approved Legal Identity](/neuron-api/guides/getting-your-identity-approved) and its signing key metadata and password.
* Confirm your provider accepts the `urn:nf:iot:leg:sc:1.0` contract schema and the payment instruction namespace used below.
* Use the [sandbox automatic approval process or arrange operator review](/build/agreements/overview#contract-approval). Submitting a template does not mean it is already approved.
* Use an XML editor or validator that supports XSD validation; follow [local XML validation](/resources/validate-xml).

## 1. Define the contract

Download [acknowledgement.xml](/downloads/examples/acknowledgement.xml). The complete file is shown below; you can also start with an empty file and add its sections in this order.

| Section               | Purpose                                                              | What you can adapt                                                       |
| --------------------- | -------------------------------------------------------------------- | ------------------------------------------------------------------------ |
| `contract` attributes | Set visibility, template eligibility, duration, and archival periods | Review these periods and visibility with your provider and participants. |
| `Nop`                 | Supply a schema-defined machine-readable instruction                 | Replace it only with a supported instruction and its exact schema.       |
| `role`                | Require one `Participant`                                            | Keep this name aligned with the API's `Parts` entry.                     |
| `parts`               | Mark the document as a template                                      | The instance receives actual Legal Identity identifiers.                 |
| `parameters`          | Require `Subject`, between 1 and 120 characters                      | Keep the API parameter name and human text reference aligned.            |
| `humanReadableText`   | Explain the acknowledgement and retention terms                      | Present the resulting instance text before requesting a signature.       |

```xml theme={null}
<?xml version="1.0" encoding="utf-8"?>
<contract xmlns="urn:nf:iot:leg:sc:1.0"
          canActAsTemplate="true" visibility="CreatorAndParts"
          duration="P1M" archiveReq="P1M" archiveOpt="P1M">
  <Nop xmlns="https://paiwise.tagroot.io/Schema/PaymentInstructions.xsd" />
  <role name="Participant" minCount="1" maxCount="1">
    <description xml:lang="en"><paragraph><text>The participant acknowledging the stated subject.</text></paragraph></description>
  </role>
  <parts><templateOnly /></parts>
  <parameters>
    <stringParameter name="Subject" minLength="1" maxLength="120">
      <description xml:lang="en"><paragraph><text>The subject the participant will review.</text></paragraph></description>
    </stringParameter>
  </parameters>
  <humanReadableText xml:lang="en">
    <paragraph><text>The participant acknowledges reviewing: </text><parameter name="Subject" /><text>.</text></paragraph>
    <paragraph><text>This demonstration records an acknowledgement. It instructs no payment and creates no token. The instance lasts one month, followed by one month of required archival and one month of optional archival.</text></paragraph>
  </humanReadableText>
</contract>
```

## 2. Validate the file

Load the [contract schema set](/resources/schemas) in your XML validator and validate the complete `acknowledgement.xml` file using [these steps](/resources/validate-xml).

Expected result: the schema set compiles and the contract has no XML validation errors. Correct invalid namespaces, missing required fields, or element ordering before submission.

If you introduce a custom machine-readable element, also create its XSD, load it in the local namespace map, and confirm the provider's schema resolution requirements. An arbitrary XML payload is not a verified provider-supported instruction.

## 3. Propose the template

Send the following requests over HTTPS with your account’s exact host, JWT, and application URL as `Referer`. Replace every placeholder before sending a request.

Base64-encode the complete file’s UTF-8 bytes, then send:

```http theme={null}
POST /Agent/Legal/ProposeTemplate HTTP/1.1
Host: <NEURON_HOST>
Referer: https://your-app.example/
Authorization: Bearer <JWT>
Accept: application/json
Content-Type: application/json

{
  "templateBase64": "<BASE64_OF_COMPLETE_UTF8_XML>"
}
```

The `templateBase64` field contains that encoded XML. [Propose Template](/neuron-api/api-reference/contracts/propose-contract-template) returns `Template`. Record its identifier.

In the sandbox, the submitted template enters automatic review. On other Neurons, give the identifier to the operator to arrange approval. See [Contract approval](/build/agreements/overview#contract-approval).

Retrieve it with `Legal/GetContract` using the request shown below and the template identifier to observe its lifecycle. Continue only when its state is `Approved`. If it remains `Proposed` or is `Rejected`, contact the operator before creating an instance.

## 4. Create an instance

Send the approved template identifier and the participant's approved Legal Identity to `Legal/CreateContract`:

```http theme={null}
POST /Agent/Legal/CreateContract HTTP/1.1
Host: <NEURON_HOST>
Referer: https://your-app.example/
Authorization: Bearer <JWT>
Accept: application/json
Content-Type: application/json

{
  "templateId": "<APPROVED_TEMPLATE_ID>",
  "visibility": "CreatorAndParts",
  "Parts": [{ "role": "Participant", "legalId": "<APPROVED_LEGAL_ID>" }],
  "Parameters": [{ "name": "Subject", "value": "A demonstration subject for review" }]
}
```

Record the returned `Contract` identifier separately from the template identifier. The role and parameter names are case-sensitive names from the template. Do not send empty arrays for this example.

## 5. Review and sign the instance

Retrieve the created instance using its identifier:

```http theme={null}
POST /Agent/Legal/GetContract HTTP/1.1
Host: <NEURON_HOST>
Referer: https://your-app.example/
Authorization: Bearer <JWT>
Accept: application/json
Content-Type: application/json

{
  "contractId": "<CONTRACT_ID>"
}
```

Present its human-readable text, parameters, participant identity, and `Participant` role to the signer. If any value is wrong, stop before signing.

Use the participant's existing key and its password. Calculate `keySignature` and `requestSignature` from the [contract signature formulas](/neuron-api/guides/contracts-flow#construct-a-contract-signature), using the key's `keyId`, `localName`, and `namespace`, the account password, and a fresh nonce. Bind the signature to the reviewed `contractId`, `legalId`, and role `Participant`.

The key namespace is algorithm metadata retained during [key creation](/neuron-api/guides/creating-cryptographic-keys). It is not the contract XML namespace.

After the signer confirms the exact contract and role, submit the signature explicitly:

```http theme={null}
POST /Agent/Legal/SignContract HTTP/1.1
Host: <NEURON_HOST>
Referer: https://your-app.example/
Authorization: Bearer <JWT>
Accept: application/json
Content-Type: application/json

{
  "keyId": "<SIGNER_KEY_ID>",
  "legalId": "<SIGNER_LEGAL_ID>",
  "contractId": "<REVIEWED_CONTRACT_ID>",
  "role": "Participant",
  "nonce": "<FRESH_NONCE>",
  "keySignature": "<CALCULATED_KEY_SIGNATURE>",
  "requestSignature": "<CALCULATED_REQUEST_SIGNATURE>"
}
```

Retrieve the instance again with `Legal/GetContract` and the same `contractId`.

Check the returned participant signature and contract lifecycle state. A successful signature request alone does not establish that every provider requirement is satisfied. For multiple parties, repeat review and signing in each party's authorized application session using the [contract lifecycle guide](/neuron-api/guides/contracts-flow).

## Recover and retain the result

| Failure                                | Next action                                                                                                                                  |
| -------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------- |
| Template still proposed or rejected    | Retrieve its status and resolve the provider review. Do not repeatedly create instances.                                                     |
| Missing participant or invalid subject | Correct the `Parts` or `Parameters` values against the approved template.                                                                    |
| Signature rejected                     | Check approved identity, assigned role, exact host, key metadata, and the two distinct passwords. Generate a fresh nonce.                    |
| Request times out after submission     | Retrieve the known object or reconcile with the provider before retrying a write. These operations do not document an idempotency guarantee. |

Retain the template ID, instance ID, reviewed parameters, participant identity, and observed signature/lifecycle result. The example defines duration and archival periods; deleting your local files does not delete a signed contract. Follow the provider's supported lifecycle and retention rules.

Continue with [a token and state machine](/build/tokenized-assets/from-scratch), or adapt a [LegalLab example](/resources/contract-examples) to a different agreement.
