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

# Coaching portal

# Coaching portal configuration

Generates the document imported by **Portal customisation → Coaching portal → Import configuration**.

This is the largest of the three documents: it covers the portal's vertical, its feature toggles, its coaching plan, and the page content for every language.

Every field is optional — omitted fields keep their current value. Languages are only ever **added**, never removed, so an import cannot delete existing translated content.

## Document

```json theme={null}
{
  "kind": "coaching-portal",
  "version": 1,

  "use_case": "simulation",

  "features": {
    "interview_coach_enabled": true,
    "resume_check_enabled": false,
    "cover_letter_enabled": false,
    "trivia_enabled": false,
    "homepage_pricing_enabled": false,
    "purchase_credits_enabled": false
  },

  "labels": {
    "catalogue": "Case library",
    "sessions": "Simulations",
    "plan": "Placement plan",
    "session-singular": "patient simulation",
    "session-plural": "patient simulations",
    "coach": "Simulated patient"
  },

  "coaching_plan_tags": ["osce-basics-en", "osce-cardiology-en"],
  "catalogue_start_tag": "osce-home-en",

  "languages": ["en"],

  "pages": [
    {
      "language": "en",
      "public_home_blocks": [
        {
          "id": "hero",
          "type": "hero",
          "kicker": "Clinical simulation",
          "title": "# Practise with _real_ patients, safely",
          "body": "Talk to an AI patient, get scored, repeat until it is second nature.",
          "ctaLabel": "Start training",
          "ctaHref": "/home"
        },
        {
          "id": "stats",
          "type": "stats",
          "items": [
            { "value": "120", "label": "Case scenarios" },
            { "value": "24/7", "label": "Available" }
          ]
        }
      ],
      "signed_in_home_blocks": [
        {
          "id": "notice",
          "type": "rich-text",
          "body": "Start with the cardiology cases before Thursday's assessment.",
          "boxed": true
        }
      ],
      "support_page_markdown": "## Getting help\n\nContact simulation@example.org."
    }
  ]
}
```

## Top-level fields

| Field                 | Type      | Notes                                                                                                |
| --------------------- | --------- | ---------------------------------------------------------------------------------------------------- |
| `use_case`            | enum      | `job-seeker`, `corporate`, `simulation`, `education`, `custom`. Sets the default wording everywhere. |
| `features.*`          | boolean   | Only the six keys above are recognised; anything else is reported as ignored.                        |
| `labels.*`            | string    | Overrides the preset wording. Only the six keys above are recognised.                                |
| `coaching_plan_tags`  | string\[] | Ordered `catalogue_tag` ids. See the warning below.                                                  |
| `catalogue_start_tag` | string    | The directory the catalogue opens on.                                                                |
| `languages`           | string\[] | Language codes to enable.                                                                            |
| `pages[]`             | object\[] | Per-language content, keyed by `language`.                                                           |

### `use_case` and `labels`

`use_case` picks a vocabulary preset; `labels` overrides individual words on top of it. Prefer the preset and override only where the organisation genuinely uses different terminology. Overrides are portal-wide, not per language, so if the portal runs several languages, either leave `labels` out and let the preset translate, or accept that the override text appears in every language.

### `coaching_plan_tags` — must be live directories

A directory only reaches learners when it is **`visibility: public` and `status: active`**. A plan step pointing at a draft or archived directory is silently dropped from the plan — the learner sees a shorter plan with no explanation.

Only reference directories you have confirmed exist and are active. If you cannot confirm, leave `coaching_plan_tags` out entirely: with no plan configured the block is hidden rather than shown half-empty.

## Page blocks

`public_home_blocks` renders the signed-out marketing homepage. `signed_in_home_blocks` renders at the top of `/home` after sign-in — keep that one short, it sits above the learner's coaching.

Each block needs an `id` (unique within its list) and a `type`. A block with an unknown `type` is skipped and reported; the rest of the import still applies.

| `type`         | Fields                                                                                       |
| -------------- | -------------------------------------------------------------------------------------------- |
| `hero`         | `kicker`, `title` (markdown), `body` (markdown), `ctaLabel`, `ctaHref`, `imageUrl`           |
| `stats`        | `items[]` of `{ value, label }`                                                              |
| `media-text`   | `title`, `body` (markdown), `imageUrl`, `imageSide` (`left`\|`right`), `ctaLabel`, `ctaHref` |
| `feature-grid` | `title`, `columns` (2\|3\|4), `items[]` of `{ title, body, imageUrl }`                       |
| `quote`        | `quote`, `author`, `role`, `imageUrl`                                                        |
| `logo-row`     | `title`, `logos[]` of `{ imageUrl, alt }`                                                    |
| `rich-text`    | `body` (markdown), `width` (`narrow`\|`wide`), `boxed` (boolean)                             |
| `pricing`      | none — renders the configured pricing table                                                  |
| `cta`          | `title`, `body` (markdown), `ctaLabel`, `ctaHref`                                            |
| `faq`          | `title`, `items[]` of `{ question, answer }`                                                 |

Markdown fields are rendered with a restricted renderer: headings, bold, italic, lists, links. In a `hero` `title`, wrapping a word in `_underscores_` renders it as the italic accent word.

Images must be URLs that are already hosted. The importer uploads nothing.

## Rules

* Put the primary language first in `pages[]` — the editor opens on it after import.
* Blocks render in array order; that order is the page.
* A hero `ctaHref` of `/home` sends a signed-out visitor into sign-up. Use that unless there is a reason not to.
* Do not set `homepage_pricing_enabled: true` unless the portal actually sells credits; the pricing block renders empty otherwise.
