# In-app dashboard contract

The Netdata cloud-frontend dashboard (the React app that powers
`app.netdata.cloud`) renders the Integrations page from the
`integrations.js` artifact this repo produces. This guide
documents the contract between the two repositories so
maintainers know what is and is NOT in scope when working on
integrations-lifecycle changes.

The cloud-frontend repo lives at
`${NETDATA_REPOS_DIR}/dashboard/cloud-frontend/` (private,
Netdata-org). React component internals are explicitly OUT OF
SCOPE for this skill; only the artifact contract matters.

## What gets shipped

**This repo produces:** `integrations/integrations.js` (and
`integrations/integrations.json`) on every CI run of
`generate-integrations.yml` (or local run of
`gen_integrations.py`). Both files are gitignored in this
repo.

**The cloud-frontend repo consumes:**
`integrations/integrations.js` -- specifically, it copies the
file into `src/domains/integrations/data/integrations.js` in
its own source tree.

## How the consumption works

Confirmed at
`${NETDATA_REPOS_DIR}/dashboard/cloud-frontend/.github/workflows/sync-to-s3.yaml:48-66`:

1. Cloud-frontend's CI checks out `netdata/netdata` (this repo).
2. Runs `python3 integrations/gen_integrations.py` against
   the freshly checked-out master.
3. `cp ./integrations/integrations.js ../src/domains/integrations/data/integrations.js`
   into the dashboard source tree.
4. The dashboard builds with the just-copied artifact baked
   in.

A second script in the dashboard repo,
`scripts/checkIntegrations.js`, fetches
`https://raw.githubusercontent.com/netdata/netdata/master/integrations/integrations.json`
and validates against the in-tree copy as a drift detector
(`scripts/checkIntegrations.js:13`).

A third script, `scripts/checkLinks.js`, validates that links
in `src/domains/integrations/data/integrations.js` and
`src/domains/integrations/utils/integrations.js` resolve.

## The artifact shape

`integrations/integrations.js`:

```js
// DO NOT EDIT THIS FILE DIRECTLY
// It gets generated by integrations/gen_integrations.py in the Netdata repo

export const categories = [
  /* recursive tree of category objects, each:
     { id, name, description, children: [...], collector_default?: boolean }
   */
];

export const integrations = [
  /* flat array of integration objects, each carries
     integration_type, id, meta, keywords, plus the rendered
     section keys per type (e.g. setup, troubleshooting, alerts,
     metrics, functions, overview, related_resources for
     collectors) and their `clean_*` siblings (e.g. clean_setup,
     clean_alerts) */
];
```

All public content sections consumed by downstream renderers must be
markdown strings in the generated artifacts, even when the source
`metadata.yaml` stores them as structured YAML objects or arrays.
Examples: collector-like `metrics`, `alerts`, `functions`, `overview`,
`setup`, `troubleshooting`, and `related_resources` must pass through
the renderer before reaching `integrations.js` / `integrations.json`.
Leaving raw objects or arrays in these fields breaks the website Hugo
renderer and produces blank tabs or link-check failures in
cloud-frontend.

The dashboard's renderer interprets the `{% details %}` /
`{% /details %}` markers embedded in the rendered text (the
`clean=False` variant is the one written into the `.js` file).
This is why the dashboard receives rich-text content with
collapsible sections, while GitHub-rendered `.md` files use
the `clean=True` variant where these markers are stripped.

## Special case: `deploy` integrations

`deploy` entries are NOT written to disk as per-integration
`.md` files (see `per-type-matrix.md`). They live ONLY inside
`integrations.js`, sorted by `quick_start` integer. The
dashboard's "Add Nodes" dialog is the consumer.

`quick_start: -1` (or any negative) hides the entry from the
dialog. Positive values define the sort order.

## Drift detection

The cloud-frontend's `checkIntegrations.js` is the only
end-to-end drift check between the two repos. It runs in the
dashboard's CI and surfaces a failure if the local copy
diverges from `netdata/master`. There is no symmetric check
in this repo (this repo doesn't know what version of
`integrations.js` the dashboard currently has baked in).

In practice this means:

- A PR in this repo that changes `metadata.yaml` does NOT
  break the dashboard immediately. The dashboard rebuilds on
  its own schedule (or when its developers re-run their
  sync-to-s3 workflow).
- A breaking change to the `integrations.js` shape (e.g. a
  removed top-level field) WILL break the dashboard on the
  next sync. There is no shape-versioning today; both repos
  assume the JS export shape is stable.

## What is OUT of scope for integrations-lifecycle

- **The React renderer** in cloud-frontend that turns
  `integrations.js` into UI. Not documented here.
- **The Integrations page UX, search behavior, filtering,
  navigation.** Cloud-frontend territory.
- **The "Add Nodes" dialog flow** beyond the `quick_start`
  sort contract.
- **Per-platform install commands rendering** (the `deploy`
  entries' `methods[].commands[]`). The dashboard renders
  them; the metadata produces them.

## Maintainer rules

1. **Treat `integrations.js` as a published artifact**. Its
   shape (the two named exports, the per-integration object
   keys) is a contract. Avoid breaking changes; coordinate
   with the cloud-frontend team if a key must be renamed or
   removed.
2. **Render structured metadata before publication**. A new
   integration type that reuses collector-style sections must
   include every structured content key in its render-key list.
   Do not publish raw `metrics` objects, `alerts` arrays, or
   similar YAML structures under the public markdown section
   names.
3. **Custom Jinja markers in metadata** (`{% details %}`,
   `{% relatedResource %}`, `{% if %}`) are part of the
   contract. The dashboard's renderer interprets them. Test
   any new marker against both surfaces before relying on it.
4. **Do not commit `integrations.js` to this repo**. It is
   gitignored on purpose; the dashboard pulls fresh on each
   build.
