# Cockpit Javascript Dependencies

Cockpit uses [Node.js](https://nodejs.org) and the
[npm](https://docs.npmjs.com/cli/) package manager to build its code and run
browser integration tests. These are not used at runtime or when
building/installing from a release tarball.

[package.json](../package.json) has two [npmjs](https://www.npmjs.com/) package
lists: runtime `dependencies` like PatternFly or React which are included into
Cockpit's pages and run in the browser; and `devDependencies` like esbuild or linters
which are only used at build/test time.

## Git builds

When building from Git, the `node_modules/` directory is managed as a git
submodule from the `node-cache` repository in the same project as the main
repository (ie: `cockpit-project/node-cache`).  That means that normal builds
won't need to run `npm install`.  Checking out the correct version of the
`node_modules` directory is managed by the script `tools/node-modules`, which
is automatically invoked from the build system on an as-needed basis, and has
good caching.  You can also do a recursive git checkout, if you'd prefer to
build in a no-network environment, but you'll lose the caching benefits.

The gitlink for `node_modules/` is always kept in sync with the `package.json`
file used to fetch that set of modules with `npm install`.

## Making changes

If you modify `package.json`, the `node_modules` will need to be regenerated,
and a new commit recorded.  That can be managed locally by running

```
tools/node_modules install
```

which will produce a commit which is available for local testing.

When you are ready to open a pull request with your changes, push the newly
created `node_modules` commit to the cache by running

```
tools/node_modules push
```

Then create a pull request with your `package.json` and `node_modules` changes.

Each pull request runs the [reposchutz](.github/workflows/reposchutz.yml)
workflow to ensure that the branch is consistent wrt. package.json and
node_modules/. This is purely read-only and does not need any secrets.

## GitHub setup notes (documentation for project admins)

This section documents the way to setup the
[node-cache](https://github.com/cockpit-project/node-cache/) repository on
GitHub. All projects in the cockpit-project organization share the same
repository.

Each project's "release" and "dependabot" workflows need write access to the node-cache
repository for taggging releases or rebuilding node_modules/ respectively.
These happen via workflow environments, whose deploy keys are set up in bot's
[setup-deploy-keys](https://github.com/cockpit-project/bots/blob/main/setup-deploy-keys)
script.

For other projects/orgs or forks, you can create a node-cache repository from
scratch manually (unless you want to fork/re-use `setup-deploy-keys`):

 - create the `node-cache` repository under the same project as the main
   repository (or fork it)
 - add a commit to that repository with a `README`.  At least one commit on a
   named branch needs to be present in order for the GitHub web UI to function
   properly (eg: generate diffs, show tree contents, etc.)
 - generate an SSH key locally, without a passphrase, without touching the disk:
   `ssh-keygen -t ed25519 -C 'node-cache deploy' -f "${XDG_RUNTIME_DIR}/deploy-key" -N ''`
 - create an environment called `node-cache upload` in the "environments" settings of the
   primary repository.
 - add the content of the private key `deploy-key` to the `node-cache upload`
   environment as a secret with the name `NODE_CACHE_DEPLOY_KEY`
 - upload the public key `deploy-key.pub` as a deploy key to `node-cache` with
   write access enabled:
   https://github.com/cockpit-project/node-cache/settings/keys/new
 - destroy the local copy: `rm ${XDG_RUNTIME_DIR}/deploy-key*`
