# Changelog

## 0.1.0

- Initial port of the Node-RED 5.0.7 runtime and editor to Python.
- Palette catalogue served from PyPI, so the palette manager's Install tab
  can search for PyRED node packages.
- Multiplayer: two open editors see each other's presence and cursors.
- Projects: git-backed flow storage, with the SSH key store that goes with
  it. Off unless `editorTheme.projects.enabled` is set and git is available.
- Benchmark flows and a load-test harness (`tools/benchflows.py`,
  `tools/loadtest.py`), plus the three defects they found: the HTTP Response
  node replaying an upstream response's headers, JSONata refusing to evaluate
  against an HTTP message, and the HTTP Request node ignoring its keep-alive
  setting.
- A native Prometheus endpoint at `<httpAdminRoot>metrics`: process, instance,
  per-node-type throughput, and backpressure as event loop lag, in-flight
  messages and the queue depth of the nodes that hold messages back. Flows can
  publish their own metrics through the ported `prometheus-metric-config` and
  `prometheus out` nodes, into the same registry.
- The wheel now ships the built editor. It was being excluded because the
  build output is git-ignored, so the package installed and served a blank
  page; the editor source, which is useless at runtime, was shipped instead.
  A build hook refuses to build a wheel without an editor.
- Flows can be kept on object storage. `flowStore` names a URL - GCS, S3,
  Azure, a directory - and obstore syncs to it: the store wins at start-up,
  the local file is pushed on every deploy, and the editor gains an "Object
  storage" menu to force either direction. Settings can now also come from a
  `[tool.pyred]` table in the working directory's `pyproject.toml` and from
  `PYRED_*` environment variables.
- Secrets can be read at runtime from Google Secret Manager, or from a
  directory of files as Kubernetes mounts them. `${secret:NAME}` works in any
  node property - resolved when the node is built, so a broker or a Kafka
  client gets its credential at connect time and the flow file keeps the
  placeholder - and a `secret` node puts one on a message for the per-call
  case. Values are cached for `secrets.ttl`, so a rotation needs no rebuild.
- Kafka: a `kafka-broker` configuration node with `kafka in` and `kafka out`,
  the same shape as the MQTT nodes. On confluent-kafka, with any librdkafka
  setting reachable through a properties table. Values are JSON in both
  directions; a record that is not valid JSON raises an error rather than
  travelling on. `tools/kafka/compose.yml` brings up a broker to develop
  against.
- A container image, built in three stages with `uv`: Node builds the editor,
  uv resolves the environment, and the runtime image carries neither. Proxy,
  internal package index and internal npm registry are build arguments. Your
  own CA can be baked in or mounted, and reaches httpx, obstore, Python's ssl,
  certifi and librdkafka - the last of which ignores `SSL_CERT_FILE` and now
  takes its default `ssl.ca.location` from the container's bundle.
- The distribution is now **pyflowred** on PyPI; `pyred` there belongs to an
  unrelated project. The import package, the editor and the `pyred` command
  are unchanged, and `pyflowred` works as a command too.
- A second image. `Dockerfile` installs the released package with uv and
  carries no build tooling; `Dockerfile.source` is the previous one, which
  builds this checkout. Build arguments no longer leak into the runtime, and
  both images carry uv with a writable environment so the palette manager
  works.
