# What the kernel checks

> Seven checks and the exact error for each.

## When checks run

The kernel refuses a broken composition before any plugin code runs. Every failure is a thrown
error in two lines: what is wrong, then how to fix it. The first line starts with the framework id
in brackets. In `@moku-labs/web` that is `[web]`.

1. `createPlugin`: the plugin spec is checked, for example `events` must be a function.
2. `createApp`: names and dependencies are checked, before any `createState` or `onInit`.
3. `app.start()`: the app must not be started twice.

| Phase | What is checked |
| --- | --- |
| `createPlugin` | The shape of the spec. |
| `createApp` | Unique names, reserved names, core plugin names, every dependency present and earlier in the list. |
| `start` and `stop` | `start()` once per app, `stop()` only after `start()`. |

Type errors come first. Most mistakes on this page also fail `tsc`, so an editor shows them as you
type. The runtime checks catch the rest: a list built at runtime, a cast, plain JavaScript.

## The checks

Each message below is captured from the installed kernel when the site is built, by making the
mistake for real. It is never typed by hand, so it cannot drift from what your app prints.

- `duplicate-name` · checked at `createApp`

  ```text
  [web] Duplicate plugin name: "auth".
    Each plugin must have a unique name.
  ```

  Fix: List each plugin once in createApp({ plugins }).

- `missing-dependency` · checked at `createApp`

  ```text
  [web] Plugin "billing" depends on "auth", but "auth" is not registered.
    Add "auth" to your plugin list before "billing".
  ```

  Fix: Add the plugin it depends on to the plugins list.

- `dependency-order` · checked at `createApp`

  ```text
  [web] Plugin "billing" depends on "auth", but "auth" appears after "billing".
    Move "auth" before "billing" in your plugin list.
  ```

  Fix: Put a dependency before the plugin that depends on it.

- `reserved-name` · checked at `createApp`

  ```text
  [web] Plugin name "start" conflicts with a reserved app method.
    Choose a different plugin name.
  ```

  Fix: Rename the plugin: start, stop, emit and require are app methods.

- `core-plugin-clash` · checked at `createApp`

  ```text
  [web] Plugin name "log" conflicts with core plugin "log".
    Choose a different plugin name.
  ```

  Fix: Rename the plugin: log and env are core plugins on every ctx.

- `events-object` · checked at `createPlugin`

  ```text
  [web] Plugin "analytics" has invalid events: expected a function.
    Provide a function like: events: register => ({ "event:name": register<PayloadType>() })
  ```

  Fix: Declare events with a function: events: register => ({ ... }).

- `double-start` · checked at `start`

  ```text
  [web] App already started.
    start() can only be called once.
  ```

  Fix: Call app.start() once per app.

## Why errors and not warnings

An agent reads errors. It skims warnings. A startup error with the plugin name in it is the
cheapest review step in the lifecycle, so the kernel makes it impossible to skip.


Source: https://moku-labs.com/docs/concepts/kernel-checks/ · @moku-labs/core@1.7.6
