Single-node Setup with k0s
k0s provides a lightweight Kubernetes distribution that is well suited to a single-node Geocore installation. This guide uses an Ubuntu Server host and follows the recommendations for a single-machine deployment.
Before you beginComplete the OnPremise prerequisites first. In particular, make sure that you can access the Centiloc Harbor registry and thatkubectland Helm are available on the host.
On a clean Ubuntu Server host, install and start a single-node k0s controller:
curl -sSLf https://get.k0s.sh | sudo sh
sudo k0s install controller --single
sudo systemctl daemon-reload
sudo k0s start
sudo k0s kubeconfig admin > ~/.kube/config
Confirm that the node is ready:
kubectl get nodes
The output should show one node with the Ready status:
NAME STATUS ROLES AGE VERSION
myk0s Ready control-plane 1d v1.28.2+k0s
For a single node, Geocore can deploy PostgreSQL in the cluster. Create a directory on the host for its persistent data:
sudo mkdir -p /opt/geocore/pg/data
sudo chown $USER:$USER -R /opt/geocore
sudo chmod 777 -R /opt/geocore
Create a myvalues.yaml file. The following sections are intentionally independent: add each one to the same file and replace every placeholder with your own values.
Configure the Harbor credentials, the single-node stream settings, the PostgreSQL credentials used by Geocore, and the current Keycloak setting:
global:
imageCredentials:
registry: harbor.centiloc.com
email: <your-email>
password: <your-password>
username: <your-username>
configuration:
streamTech: "KAFKA"
keycloak:
url: ""
postgresql:
primary:
user: "custom_user"
password: "strong_password"
dbname: "db_geocore"
replicas: []
postgresql:
enabled: true
auth:
postgresPassword: "very_strong_password"
storagePath: "/opt/geocore/pg/data"
kafka:
enabled: true
replicaCount: 1
Keycloak is currently unavailableThe current Geocore OnPremise chart does not include Keycloak. Keepglobal.keycloak.urlempty.
MQTT must remain directly reachable by boards. Expose the broker as a NodePort. The following configuration enables TLS by default; replace X.X.X.X with the IP address of the k0s host.
emqx:
enabled: true
replicaCount: 1
allPassword: "very_strong_password"
service:
type: NodePort
nodePorts:
mqttssl: 30883
mqtt: 30881
emqxConfig:
EMQX_SSL_CLIENT_OPTS__SERVER_NAME_INDICATION: "X.X.X.X"
# To enable plain TCP instead, comment the line above and uncomment:
# EMQX_LISTENERS__TCP__DEFAULT__ENABLE: "true"
Expose the Geocore NTP service as a NodePort on the same address as MQTT:
ntp:
service:
type: NodePort
By default, the service is available on UDP port 30123. Boards require UDP port 123, which is outside Kubernetes’ NodePort range. Redirect UDP port 123 to port 30123 on the host.
Install nftables:
sudo apt-get update
sudo apt install nftables
Identify the host network interface that receives board traffic:
ip -o addr | grep 'k0s_single_machine_cluster_IP' | awk '{print $2}'
Add the following rule to /etc/nftables.conf, replacing your_interface_name with the interface name:
table ip geocore {
chain prerouting {
type filter hook prerouting priority mangle; policy accept;
iifname "your_interface_name" udp dport 123 \
dup to 127.0.0.1 udp dport set 30123 notrack
}
chain input {
type filter hook input priority mangle; policy accept;
iifname lo udp dport 123 ip daddr set 127.0.0.1 notrack
}
}
Apply the configuration:
sudo nft -f /etc/nftables.conf
RS485 support is disabled by default. Enable the gateway agent only if the deployment needs it:
parcontrol3:
gwagent:
replicaCount: "1"
Choose one access method and add its configuration to myvalues.yaml. See Service Exposure for the complete exposure model.
Use the Contour Envoy LoadBalancer when the API and Centui should be available on standard HTTPS ports. The following values configure the TLS setup:
core:
geo:
tlsEnabled: true
centui:
tlsEnabled: true
apiURL: "api.k0s.example.test"
centuiURL: "centui.k0s.example.test"
The apiURL and centuiURL values must exactly match the api.domain and centui.domain values in the Ingress configuration. Point both names to the Contour Envoy address.
Keep the Geocore services as ClusterIP. Expose the Contour Envoy service as a NodePort and point both DNS names, or equivalent client hosts-file entries, to the k0s host IP address.
core:
geo:
tlsEnabled: false
centui:
tlsEnabled: false
apiURL: "api.k0s.example.test:30180"
centuiURL: "centui.k0s.example.test"
After installing Contour with Envoy HTTP NodePort 30180 and the Geocore routes, open Centui at http://centui.k0s.example.test:30180. Centui reaches the Envoy gRPC-Web endpoint at http://api.k0s.example.test:30180.
Follow Install Contour and Envoy and select the plain HTTP routing values in the Ingress guide.
Once myvalues.yaml contains the required sections, install Geocore in the geocore namespace:
helm install geocore oci://harbor.centiloc.com/centiloc/geocore \
--namespace geocore \
--create-namespace \
-f myvalues.yaml
Check that the pods are running:
kubectl get pods --namespace geocore
MQTT and NTP are exposed through the NodePorts configured above. Continue with Expose Geocore Services to install Contour, create the mandatory Geocore routes, and publish DNS records. Then open Centui at the configured Envoy address.
To remove the k0s cluster, follow the official k0s reset instructions.