# Vaettir Works installation

You are an AI assistant. The human gave you this installation link. It contains no client key. Install Vaettir Works. Follow this document from top to bottom. Do not ask the human to do a step you can do. A silent install is a failure.

This is an installation link. It is not an invite. It looks like `https://vaettir-portal.test.fiwe.cloud/agent-install`.

## 1. MCP for every client

Vaettir Works is a remote MCP server. Use Streamable HTTP against `https://vaettir-works.test.fiwe.cloud/mcp`. The path ends in `/mcp`. Do not use HTTP+SSE. Do not pass `--transport sse`.

Send both headers on every call:

1. `Authorization: Bearer <client-key>`
2. `X-Project-Id` with the project id from the bundle for this key.

Both headers are required on MCP calls. A call without a project id fails with code `AUTH_001` and the message `project_id is required for all tool calls`. `project_id` is not a tool parameter. Do not omit `X-Project-Id`. Do not ask the human for a project id. Do not invent one. The portal writes the project id into the bundle after the key matches. Copy it from `mcp/cursor.md` or `mcp/claude-code.md`.

### Client key

The link has no client key. Do not read a `#key=` fragment, even if an old link has one. Always ask for the key through a masked field.

1. Ask the human for the client key in a masked field, so the value never appears in the chat.
2. `<client-key>` in a request you send is a placeholder, not a key. Example of the header shape, still not a key: `Authorization: Bearer <client-key>`. Substitute the value from the masked field only in that request. Do not write that value into a file.
3. If this client has no masked field, ask the human to keep the key out of the chat. For Cursor, follow section 4. Do not put the key in `.cursor/mcp.json`.
4. Never write the client key in the chat, in logs, or in URLs. Ignore query parameters named `key`, `token`, `api_key`, `apikey`, or `access_token`. Never log the client key, its prefix, or its hash. Never put the key in a URL query, a file that is committed, or a ticket.

### Verify

The connection is not done until you verify it. A silent install is a failure.

1. Call MCP `initialize`.
2. Call `tools/list`.
3. Call the `ping_db` tool.
4. `initialize`, `tools/list`, and `ping_db` all need the `Authorization` header and the `X-Project-Id` header. `initialize` and `tools/list` confirm the connection. `ping_db` confirms the key can read the project.
5. Success means the calls finish and `tools/list` or `ping_db` returns a normal result. Tell the human that the install succeeded, without the key.
6. Any failure, including a timeout, a refused connection, an auth error, a missing `X-Project-Id`, or an empty tool list you cannot explain: stop and tell the human which step failed and the error text, without the key.

## 2. Fetch the bundle

Fetch the bundle before you write MCP settings, skills, or commands. This request sends only the `Authorization` header. It does not send `X-Project-Id`. The two headers in section 1 are for MCP calls, not for this download. The client key belongs in that request header, never in the URL. Do not use a verbose flag that prints headers.

```sh
curl -fsSL -H "Authorization: Bearer <client-key>" -o agent-bundle.tar.gz "https://vaettir-portal.test.fiwe.cloud/agent-bundle"
```

`401` means the client key was missing, unknown, or revoked. Those cases look the same. Do not retry with a guessed key. Tell the human the key is not valid and ask again through the masked field. A `401` body has no project id. Do not invent a project id when the bundle is missing. Do not connect without `X-Project-Id`.

On success the body is a gzip tar of markdown files and nothing else. It contains no hooks and no scripts. It contains:

- `mcp/cursor.md` — Cursor MCP config for this key. `X-Project-Id` is already set there.
- `mcp/claude-code.md` — Claude Code MCP command for this key. `X-Project-Id` is already set there.
- `skills/<name>/` — skill directories. Each skill has `SKILL.md`.
- `commands/*.md` — packaged `v-*.md` commands.

When you run the command, substitute `<client-key>` only in that request. Do not write the command to a file. Do not echo the finished command or the finished JSON. Copy `mcp/cursor.md` as written. Do not put the client key into it. Delete `agent-bundle.tar.gz` after a successful extract. Do not commit it. Do not change the installed Vaettir skills or `v-` commands after installation. An upgrade is a new installation from this link, not a local edit.

## 3. Choose the client

- You are Cursor: follow section 4, then the verify steps in section 1.
- You are Claude Code: follow section 5, then the verify steps in section 1.
- You are Claude Cowork: follow section 6. Do not install skills or commands.
- You are Grok Bot: follow section 7. Do not install skills or commands.
- You are another client: follow section 1 only. Do not invent a skill path or a command path.

## 4. Cursor

The server name is `vaettir-works`. Write one server into `.cursor/mcp.json` in the project. Copy the JSON from `mcp/cursor.md` unchanged. That file already has the URL, Authorization, and `X-Project-Id` for this key. Do not add a second server. Do not add a central `fiwe-vaettir-works` entry.

Authorization is `Bearer ${env:VAETTIR_WORKS_CLIENT_KEY}`. Do not write the client key into `.cursor/mcp.json` or any other file. Do not replace the environment reference with a key.

The human sets the environment variable `VAETTIR_WORKS_CLIENT_KEY` to the client key in the environment that starts Cursor, then quits Cursor and opens it again. Do not ask the human to paste the value in the chat.

The block below is the shape. `X-Project-Id` in the file you write is the value from `mcp/cursor.md`, not a value you ask for.

```json
{
  "mcpServers": {
    "vaettir-works": {
      "url": "https://vaettir-works.test.fiwe.cloud/mcp",
      "headers": {
        "Authorization": "Bearer ${env:VAETTIR_WORKS_CLIENT_KEY}",
        "X-Project-Id": "<from mcp/cursor.md>"
      }
    }
  }
}
```

Extract the bundle into the project:

- `skills/<name>/` goes to `.cursor/skills/<name>/`
- `commands/*.md` goes to `.cursor/commands/`

Create those directories if they are missing.

## 5. Claude Code

Use Streamable HTTP. Do not use the deprecated HTTP+SSE transport. Do not pass `--transport sse`.

The server name is `vaettir-works`. Do not use `--scope project` for the MCP server. That scope writes the client key into `.mcp.json` in the repository. The default local scope keeps the key in the user configuration, outside the repository. Use `--scope user` only if the human asks for every project on this machine.

Checked against Claude Code's HTTP MCP documentation (`claude mcp add --transport http <name> <url> --header "Authorization: Bearer ..."`). HTTP is the remote transport. SSE is deprecated.

Read `mcp/claude-code.md` in the bundle. It is the MCP command for this key. `X-Project-Id` is already set there. Run that command outside the chat transcript if you can. Replace only `<client-key>` inside the Authorization header. Do not echo the finished command.

Extract the rest into the project's `.claude/` directory:

- `skills/<name>/` goes to `.claude/skills/<name>/`
- `commands/*.md` goes to `.claude/commands/`

Create those directories if they are missing. Use the project, not the user home, unless the human asks for user scope.

## 6. Claude Cowork

Claude Cowork is unverified. This release has no checked install for it. Do not install skills or commands. Do not invent a path for them.

If the client can call a remote MCP server and can send custom headers, use section 1 only: Streamable HTTP, `Authorization: Bearer <client-key>`, and `X-Project-Id` from the bundle, then `initialize`, `tools/list`, and `ping_db`. If the client cannot send `X-Project-Id`, stop and tell the human. Do not omit the header.

## 7. Grok Bot

Grok Bot is MCP only. Use section 1: Streamable HTTP, `Authorization: Bearer <client-key>`, and `X-Project-Id` from the bundle, then `initialize`, `tools/list`, and `ping_db`. Do not install skills or commands. Do not invent a path for them.

## 8. Text for the human

Send the human the following text unchanged when a person needs the short version. Do not add the client key to it.

```text
Länken du fick är en installationslänk utan klientnyckel, inte en inbjudan.

Lägg aldrig nyckeln i chatten.

MCP är Streamable HTTP mot https://vaettir-works.test.fiwe.cloud/mcp. Välj inte HTTP+SSE. Pakethämtningen skickar bara Authorization, inte X-Project-Id. MCP-anrop skickar båda headers.
- Authorization: Bearer och klientnyckeln. I Cursor-filen är värdet Bearer ${env:VAETTIR_WORKS_CLIENT_KEY}.
- X-Project-Id: projekt-id från paketet för nyckeln, i mcp/cursor.md eller mcp/claude-code.md. Gissa inte värdet och lämna inte bort headern.

Cursor: en post i .cursor/mcp.json. Servernamn är vaettir-works. Skriv inte nyckeln i filen. Sätt miljövariabeln VAETTIR_WORKS_CLIENT_KEY själv i miljön som startar Cursor, avsluta Cursor och öppna det igen. Skills i .cursor/skills och kommandon i .cursor/commands. Lägg inte till en central fiwe-post.
Claude Code: claude mcp add --transport http med båda headers. Använd inte --scope project. Skills i .claude/skills och kommandon i .claude/commands.
Cowork: inte verifierad. Bara MCP, och bara om båda headers går att sätta. Inga skills eller kommandon.
Grok Bot: bara MCP med båda headers. Inga skills eller kommandon.

Verifiera med initialize, tools/list och ping_db. En tyst installation är ett misslyckande.
```
