Node-RED on GKE Autopilot — Lab Guide
Overview
Estimated time: 1–2 hours
Node-RED is a flow-based programming tool for event-driven applications — originally designed for IoT but now widely used for API integration, data transformation, home automation, and MQTT-based messaging. This lab deploys Node-RED on GKE Autopilot backed by Cloud Filestore NFS for persistent flow storage. No database is required.
What the Module Automates
- GKE Autopilot cluster (via Services GCP prerequisite)
- Kubernetes namespace, Deployment, and LoadBalancer Service
- Cloud Filestore NFS instance mounted at
/datafor persistent flow storage - Cloud Storage bucket for backups and artifacts
- Artifact Registry repository and optional container image mirroring
- Secret Manager secret for the Node-RED credential encryption key (
NODE_RED_CREDENTIAL_SECRET) - Workload Identity binding for GCS access
- Static external IP reservation
- Cloud Monitoring uptime checks
What You Do Manually
- Note the deployment outputs (external IP, namespace, etc.) from the RAD UI deployment panel
- Connect
kubectlto the GKE cluster and verify the Node-RED pod - Access the Node-RED editor in your browser
- Explore the editor layout (palette, canvas, debug panel)
- Build a flow that makes an HTTP request and logs the response
- Create an HTTP endpoint and test it with
curl - Verify flow persistence across pod restarts (NFS-backed
/data) - Check the node-red-dashboard package (if installed)
- Review Cloud Logging and Cloud Monitoring
CLI and REST API Overview
This lab uses the following CLI tools:
| Tool | Purpose |
|---|---|
gcloud | GCP project and cluster management |
kubectl | Kubernetes workload inspection and pod restarts |
curl | Testing Node-RED HTTP endpoints |
Key REST APIs exercised:
| API | Description |
|---|---|
http://<EXTERNAL_IP>:1880 | Node-RED editor UI |
http://<EXTERNAL_IP>:1880/my-endpoint | Custom HTTP endpoint created in Phase 5 |
https://container.googleapis.com/v1/... | GKE Cluster API |
Prerequisites
Before deploying, ensure the following:
- Services GCP module is deployed (provides VPC, GKE cluster, Filestore NFS).
gcloudCLI is authenticated:gcloud auth application-default loginkubectlis installed.- You have a GCP project with billing enabled.
- Access to the RAD UI with permission to deploy modules in the target GCP project.
Phase 1 — Deploy [AUTOMATED]
Duration: 10–20 minutes
Variables
In the RAD UI, open the NodeRED GKE module and fill in the deployment form:
| Variable | Required | Default | Description |
|---|---|---|---|
project_id | Yes | — | GCP project ID (e.g., my-project-123) |
region | No | us-central1 | GCP region for deployment |
deployment_id | No | auto-generated | Short alphanumeric suffix appended to all resource names |
tenant_deployment_id | No | demo | Environment identifier (e.g., prod, dev) |
application_name | No | nodered | Internal app identifier (must be lowercase) |
application_version | No | latest | Docker Hub tag for nodered/node-red (e.g., 4.0.9) |
deploy_application | No | true | Set to false to provision infrastructure only |
min_instance_count | No | 1 | Minimum pod replicas (must be at least 1 for GKE) |
max_instance_count | No | 1 | Maximum pod replicas (keep low — flows are stateful) |
gke_cluster_name | No | auto-discovered | Name of the GKE Autopilot cluster |
enable_nfs | No | true | Provision Cloud Filestore NFS and mount at /data |
nfs_mount_path | No | /data | NFS mount path inside the container |
create_cloud_storage | No | true | Provision GCS bucket for backups |
enable_iap | No | false | Enable Identity-Aware Proxy for Google identity auth |
enable_redis | No | false | Enable Redis for Node-RED context storage |
redis_host | No | "" | Redis server IP (required when enable_redis = true) |
container_image_source | No | prebuilt | prebuilt deploys the official nodered/node-red image |
container_resources | No | { cpu_limit = "500m", memory_limit = "512Mi" } | CPU/memory limits for the Node-RED container |
Deploy
Click Deploy in the RAD UI.
Approximate Phase Durations
| Step | Duration |
|---|---|
| NFS Filestore provisioning | 3–5 minutes |
| GKE Deployment rollout | 2–5 minutes |
| Total | ~10–20 minutes |
Outputs
After deployment completes, the following outputs are available in the RAD UI deployment panel:
| Output | Description |
|---|---|
kubernetes_ready | True when all Kubernetes resources are deployed |
Set shell variables for use in later steps:
export PROJECT="your-gcp-project-id" # set this first — your GCP project ID
export REGION="us-central1" # the region you deployed into
export TOKEN=$(gcloud auth print-access-token)
# Discover the GKE cluster
export CLUSTER=$(gcloud container clusters list \
--project=${PROJECT} \
--format="value(name)" \
--limit=1)
# Configure kubectl
gcloud container clusters get-credentials ${CLUSTER} \
--region=${REGION} \
--project=${PROJECT}
# Discover the namespace (pattern: appnodereddemo<deploymentid>)
export NAMESPACE=$(kubectl get namespaces --no-headers \
-o custom-columns=":metadata.name" | grep "^appnodered" | head -1)
# Discover the external IP
export EXTERNAL_IP=$(kubectl get svc -n ${NAMESPACE} \
-o jsonpath='{.items[0].status.loadBalancer.ingress[0].ip}')
Phase 2 — Connect kubectl and Verify Pod [MANUAL]
Duration: 5 minutes
Steps
-
Fetch GKE credentials:
gcloud container clusters get-credentials <CLUSTER_NAME> \
--region <REGION> \
--project <PROJECT_ID>gcloud equivalent for listing clusters:
gcloud container clusters list --project <PROJECT_ID>REST API equivalent:
curl -H "Authorization: Bearer $(gcloud auth print-access-token)" \
"https://container.googleapis.com/v1/projects/<PROJECT_ID>/locations/<REGION>/clusters" -
Find the Node-RED namespace:
kubectl get namespaces | grep nodered -
Verify the pod is running:
kubectl get pods -n "${NAMESPACE}"Expected result: One pod in
Runningstate with1/1containers ready. -
Check Node-RED startup logs:
kubectl logs -n "${NAMESPACE}" -l app=nodered --tail=30Watch for:
Node-RED version: v<VERSION>,Starting flows,Started flows. -
Note the external IP:
kubectl get service -n "${NAMESPACE}"Copy the
EXTERNAL-IPvalue — you will use it throughout the lab.
Phase 3 — Explore the Node-RED Editor [MANUAL]
Duration: 5 minutes
Steps
-
Open your browser and navigate to:
http://<EXTERNAL_IP>:1880Node-RED listens on port 1880.
-
If authentication is configured (IAP or Node-RED credentials), log in. By default, no authentication is required.
-
Take a tour of the editor layout:
- Left panel (Palette): All available node categories — Input, Output, Function, Network, Sequence, Parser, Storage, etc. Scroll through to see the variety.
- Center panel (Canvas/Flow editor): Where you wire nodes together into flows. Currently empty on a fresh deployment.
- Right panel (Info/Debug): Switches between node documentation (Info tab) and runtime debug output (Debug tab).
- Top toolbar: Deploy button (red), hamburger menu for settings and palette management.
Expected result: The editor loads with an empty canvas. The palette is populated with all built-in node types.
-
gcloud logging equivalent (view Node-RED logs):
gcloud logging read \
'resource.type="k8s_container" AND resource.labels.container_name="nodered"' \
--project=<PROJECT_ID> \
--limit=30 \
--format="table(timestamp,textPayload)"
Phase 4 — Build Your First Flow [MANUAL]
Duration: 10 minutes
In this phase you build a simple flow: trigger an HTTP request and display the response in the debug panel.
Steps
-
From the palette, drag an inject node onto the canvas.
-
Drag an http request node onto the canvas to the right of the inject node.
-
Drag a debug node onto the canvas to the right of the http request node.
-
Wire them together:
- Click and drag from the output port (right side) of the inject node to the input port (left side) of the http request node.
- Click and drag from the output of the http request node to the input of the debug node.
-
Double-click the inject node to configure it:
- Set Payload to
stringwith valuetrigger - Set Repeat to
none(manual trigger only) - Click Done.
- Set Payload to
-
Double-click the http request node to configure it:
- Set Method to
GET - Set URL to
https://httpbin.org/json - Set Return to
a parsed JSON object - Click Done.
- Set Method to
-
Double-click the debug node:
- Set Output to
msg.payload - Click Done.
- Set Output to
-
Click the red Deploy button in the top right.
Expected result: The toolbar shows
Successfully deployed. -
Click the button (square icon) on the left side of the inject node to trigger the flow.
-
Click the Debug tab in the right panel.
Expected result: The JSON response from
httpbin.org/jsonappears in the debug panel, showing a parsed object withslideshowdata.
Phase 5 — HTTP Endpoints [MANUAL]
Duration: 10 minutes
In this phase you create an HTTP input endpoint and test it with curl.
Steps
-
Drag an http in node onto the canvas (from the Network category in the palette).
-
Double-click it to configure:
- Method:
POST - URL:
/my-endpoint - Click Done.
- Method:
-
Drag a function node onto the canvas next to the http in node.
-
Double-click the function node and paste the following code:
msg.payload = {
received: msg.payload,
timestamp: new Date().toISOString(),
message: "Hello from Node-RED on GKE!"
};
return msg;Click Done.
-
Drag an http response node onto the canvas.
-
Wire: http in → function → http response.
-
Click Deploy.
-
Test the endpoint with
curl:curl -X POST "http://${EXTERNAL_IP}:1880/my-endpoint" \
-H "Content-Type: application/json" \
-d '{"message": "hello from the lab"}' \
| python3 -m json.toolExpected result:
{
"received": {"message": "hello from the lab"},
"timestamp": "2026-05-15T10:00:00.000Z",
"message": "Hello from Node-RED on GKE!"
} -
Try additional HTTP methods or payload structures by modifying the function node code and redeploying.
Phase 6 — Persistent Flows and NFS Storage [MANUAL]
Duration: 10 minutes
In this phase you verify that Node-RED flows survive a pod restart — confirming the NFS-backed /data volume is working correctly.
Steps
-
Confirm the flows you deployed in Phases 4 and 5 are visible on the canvas.
-
Inspect the NFS PersistentVolumeClaim used by the Deployment:
kubectl get pvc -n "${NAMESPACE}"
kubectl describe pvc -n "${NAMESPACE}"Expected result: A PVC bound to the Cloud Filestore NFS instance appears in
Boundstate. -
Restart the Node-RED pod to simulate a pod restart or node eviction:
kubectl rollout restart deployment/nodered -n "${NAMESPACE}"
# Wait for the new pod to be ready:
kubectl rollout status deployment/nodered -n "${NAMESPACE}"Expected result: A new pod starts (the old one terminates). After 30–60 seconds, the new pod is
Running. -
Refresh the Node-RED editor in your browser (
http://<EXTERNAL_IP>:1880).Expected result: Both flows from Phases 4 and 5 are still present on the canvas. This confirms that Node-RED's
/datadirectory — which storesflows.json,flows_cred.json, and installed packages — is persisted on NFS. -
gcloud equivalent (describe the Filestore instance):
gcloud filestore instances list --project=<PROJECT_ID>REST API equivalent:
curl -H "Authorization: Bearer $(gcloud auth print-access-token)" \
"https://file.googleapis.com/v1/projects/<PROJECT_ID>/locations/-/instances"
Phase 7 — Dashboard (If Installed) [MANUAL]
Duration: 5–10 minutes
The node-red-dashboard package provides UI widgets that render at /ui. This phase is optional and depends on whether the dashboard package is installed.
Steps
-
In the Node-RED editor, click the hamburger menu (top right) and select Manage palette.
-
Click the Install tab and search for
node-red-dashboard. -
If it appears in the installed list (or if you install it now), click Install and wait for confirmation.
-
After the palette reloads, look for the dashboard category in the left palette panel.
-
Drag a ui_gauge node onto the canvas.
-
Double-click it:
- Create or select a Tab (e.g.,
Home). - Create or select a Group (e.g.,
Metrics). - Set Label to
Temperature. - Set Value format to
{{value}}. - Click Done.
- Create or select a Tab (e.g.,
-
Wire a inject node to the ui_gauge (set payload to a number, e.g.,
42). -
Click Deploy.
-
Navigate to:
http://<EXTERNAL_IP>:1880/uiExpected result: A dashboard page loads showing the gauge at the value injected. Clicking the inject button updates the gauge in real time.
Phase 8 — Explore Cloud Logging [MANUAL]
Duration: 5 minutes
Steps
-
Open the Cloud Logging console.
-
Set the project to your GCP project.
-
Query Node-RED runtime logs:
resource.type="k8s_container"
resource.labels.namespace_name="<NAMESPACE>"
resource.labels.container_name="nodered"gcloud equivalent:
gcloud logging read \
"resource.type=\"k8s_container\" resource.labels.namespace_name=\"${NAMESPACE}\"" \
--project=<PROJECT_ID> \
--limit=100 \
--format="table(timestamp,severity,textPayload)" -
Filter for flow deployment events:
textPayload=~"deploy|flow|Started" -
Filter for HTTP endpoint requests made during Phase 5:
textPayload=~"POST /my-endpoint"Expected result: Log entries showing Node-RED startup, flow deployments, and HTTP request handling. Debug node output is also visible in the logs.
Phase 9 — Explore Cloud Monitoring [MANUAL]
Duration: 5 minutes
Steps
-
Open the Cloud Monitoring console.
-
Navigate to Dashboards and look for the GKE workload dashboard.
-
Check key metrics for the Node-RED pod:
# gcloud equivalent: list available GKE metrics
gcloud monitoring metrics list \
--filter="metric.type=starts_with(\"kubernetes.io/container\")" \
--project=<PROJECT_ID> -
View in the console:
kubernetes.io/container/cpu/limit_utilization— Node-RED is lightweight; should remain below 10%kubernetes.io/container/memory/limit_utilization— depends on installed nodes and active flowskubernetes.io/pod/network/received_bytes_count— traffic from HTTP requests
-
Review the uptime check (configured with
path = "/"):REST API equivalent:
curl -H "Authorization: Bearer $(gcloud auth print-access-token)" \
"https://monitoring.googleapis.com/v3/projects/<PROJECT_ID>/uptimeCheckConfigs"Expected result: The uptime check shows passing status against the Node-RED editor root path. CPU and memory utilization are low, confirming Node-RED's lightweight footprint on GKE Autopilot.
Phase 10 — Undeploy [AUTOMATED]
Duration: 5–10 minutes
When you are finished with the lab, return to the RAD UI, navigate to your deployment, and click Undeploy (or Delete) to remove all resources provisioned by this module.
What is removed: Kubernetes Deployment, Service, namespace, Cloud Filestore NFS instance, GCS bucket, Secret Manager secrets, Artifact Registry images, static IP, Cloud Monitoring uptime checks.
What is not removed: The GKE cluster itself (managed by Services GCP), the VPC (managed by Services GCP).
Resources provisioned by the Services GCP module (VPC, Cloud SQL instance, GKE cluster) are managed separately and must be undeployed via their own RAD UI deployment entry.
Summary
| Phase | Type | Key Action | Duration |
|---|---|---|---|
| 1 — Deploy | Automated | RAD UI deployment provisions GKE workload, NFS, GCS, Artifact Registry | 10–20 min |
| 2 — Verify Pod | Manual | kubectl get pods, check logs, note external IP | 5 min |
| 3 — Explore Editor | Manual | Navigate palette, canvas, and debug panel | 5 min |
| 4 — First Flow | Manual | Wire inject → HTTP request → debug, deploy and trigger | 10 min |
| 5 — HTTP Endpoints | Manual | Create POST endpoint, test with curl | 10 min |
| 6 — NFS Persistence | Manual | Restart pod, verify flows survive, inspect PVC | 10 min |
| 7 — Dashboard | Manual | Install node-red-dashboard, add gauge widget | 5–10 min |
| 8 — Cloud Logging | Manual | Query container logs and HTTP request events | 5 min |
| 9 — Cloud Monitoring | Manual | Review GKE metrics and uptime checks | 5 min |
| 10 — Undeploy | Automated | RAD UI removes all module resources | 5–10 min |