Skip to content

Commit 302d69a

Browse files
authored
Merge pull request #10 from GeiserX/feat/helm-chart
feat: add Helm chart for Kubernetes deployment
2 parents d489941 + bf244e5 commit 302d69a

22 files changed

Lines changed: 1988 additions & 0 deletions

charts/pumperly/.helmignore

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
# Patterns to ignore when building packages.
2+
# This supports shell glob matching, relative path matching, and
3+
# negation (prefixed with !). Only one pattern per line.
4+
.DS_Store
5+
# Common VCS dirs
6+
.git/
7+
.gitignore
8+
.bzr/
9+
.bzrignore
10+
.hg/
11+
.hgignore
12+
.svn/
13+
# Common backup files
14+
*.swp
15+
*.bak
16+
*.tmp
17+
*.orig
18+
*~
19+
# Various IDEs
20+
.project
21+
.idea/
22+
*.tmproj
23+
.vscode/

charts/pumperly/Chart.yaml

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
apiVersion: v2
2+
name: pumperly
3+
description: A Helm chart for Pumperly - Open-source fuel and EV route planner
4+
type: application
5+
kubeVersion: ">=1.21.0-0"
6+
version: 0.1.0
7+
appVersion: "1.2.0"
8+
keywords:
9+
- pumperly
10+
- fuel
11+
- ev
12+
- route-planner
13+
- maps
14+
- postgis
15+
- self-hosted
16+
home: https://pumperly.com
17+
sources:
18+
- https://github.com/GeiserX/Pumperly
19+
maintainers:
20+
- name: Sergio Fernandez
21+
email: acsdesk@protonmail.com
22+
annotations:
23+
category: Maps

charts/pumperly/README.md

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,65 @@
1+
# Pumperly Helm Chart
2+
3+
This chart deploys the Pumperly web application plus optional bundled PostGIS, Valhalla, and Photon components.
4+
5+
## What This Chart Handles
6+
7+
- Pumperly web Deployment
8+
- Optional bundled PostGIS StatefulSet
9+
- Optional Valhalla routing Deployment
10+
- Optional Photon Deployment when you provide a real image and startup command
11+
- Automatic `npx prisma db push` init step for the primary database
12+
13+
## Important Notes
14+
15+
- Keep `replicaCount: 1` unless you intentionally disable or externalize scraping. Pumperly runs scrapers inside the web process.
16+
- The chart defaults the web Deployment to `Recreate` so upgrades do not overlap two scraper pods.
17+
- Photon is not plug-and-play. If `photon.enabled=true`, you must provide a working image plus `photon.command`/`photon.args`.
18+
- For external infrastructure, disable `postgis.enabled` and use `externalDatabase` plus `externalServices.valhallaUrl` / `externalServices.photonUrl`.
19+
- If you rely on chart-managed secrets, `helm upgrade` will now roll the web pod when the generated Secret changes.
20+
21+
## Minimal Example
22+
23+
```yaml
24+
ingress:
25+
enabled: true
26+
className: nginx
27+
hosts:
28+
- host: pumperly.example.com
29+
paths:
30+
- path: /
31+
pathType: Prefix
32+
33+
config:
34+
defaultCountry: ES
35+
enabledCountries: ES,FR,PT
36+
37+
apiKeys:
38+
tankerkoenig: your-key
39+
openChargeMap: your-ocm-key
40+
41+
valhalla:
42+
enabled: true
43+
```
44+
45+
Install with:
46+
47+
```bash
48+
helm upgrade --install pumperly ./charts/pumperly -f my-values.yaml
49+
```
50+
51+
## Useful Values
52+
53+
- `existingSecret`: reuse an externally managed Secret
54+
- always provide `DATABASE_URL`
55+
- if `postgis.enabled=true`, also provide `POSTGRES_USER`, `POSTGRES_PASSWORD`, and `POSTGRES_DB`
56+
- optional API key entries: `TANKERKOENIG_API_KEY`, `PUMPERLY_OCM_API_KEY`, `FUELPRICES_DK_API_KEY`
57+
- `externalDatabase.*`: required when `postgis.enabled=false` and you are not supplying a full `externalDatabase.url`
58+
- `waitForDatabase.enabled`: if you keep it enabled with an external DB, also set `externalDatabase.host` so the init container has something to probe
59+
- `waitForDatabase.timeoutSeconds`: fail startup if the database never becomes reachable instead of waiting forever
60+
- `deploymentStrategy.type`: switch back to `RollingUpdate` only if you are comfortable with overlapping scraper pods during upgrades
61+
- `postgis.enabled`: disable bundled PostGIS for managed PostgreSQL/PostGIS
62+
- `databaseInit.enabled`: run `npx prisma db push` before the app starts
63+
- `externalServices.valhallaUrl`: use an external Valhalla instance
64+
- `externalServices.photonUrl`: use an external Photon instance
65+
- `extraEnv` / `extraEnvFrom`: inject additional app settings without editing templates
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
Pumperly has been deployed successfully!
2+
3+
1. To access the Pumperly UI, follow these instructions:
4+
5+
{{- if .Values.ingress.enabled }}
6+
The Pumperly UI is accessible at:
7+
8+
{{- range .Values.ingress.hosts }}
9+
http{{ if $.Values.ingress.tls }}s{{ end }}://{{ .host }}{{ (index .paths 0).path }}
10+
{{- end }}
11+
{{- else }}
12+
NOTE: The ingress is disabled. Use port-forwarding to access the UI:
13+
14+
kubectl --namespace {{ .Release.Namespace }} port-forward svc/{{ include "pumperly.fullname" . }} 3000:{{ .Values.service.port }}
15+
16+
Then access the UI at: http://127.0.0.1:3000/
17+
{{- end }}
18+
19+
{{- if .Values.postgis.enabled }}
20+
2. PostGIS is running as a StatefulSet with the postgis/postgis image (spatial extensions included).
21+
{{- else }}
22+
2. PostGIS is disabled. The chart expects an external database via existingSecret or externalDatabase values.
23+
{{- end }}
24+
{{- if .Values.databaseInit.enabled }}
25+
Prisma schema sync is enabled through an initContainer on the web Deployment.
26+
{{- end }}
27+
28+
{{- if .Values.valhalla.enabled }}
29+
30+
3. Valhalla routing engine is ENABLED.
31+
- First startup will download and build routing tiles. This can take hours and requires ~15-24GB RAM.
32+
- Tile URLs: {{ .Values.valhalla.tileUrls }}
33+
- Once tiles are built, subsequent restarts are fast (tiles persist on the PVC).
34+
{{- else }}
35+
36+
3. Valhalla routing engine is DISABLED. Enable it with:
37+
--set valhalla.enabled=true
38+
{{- end }}
39+
40+
{{- if .Values.photon.enabled }}
41+
42+
4. Photon geocoder is ENABLED.
43+
NOTE: Photon requires a working image plus command/args supplied in values.
44+
The chart will not bootstrap Photon automatically for you.
45+
See: https://github.com/komoot/photon
46+
{{- else }}
47+
48+
4. Photon geocoder is DISABLED. Enable it with:
49+
--set photon.enabled=true
50+
NOTE: Photon requires a prepared image/entrypoint and large persistent storage. See chart documentation.
51+
{{- end }}
52+
53+
5. Scaling note:
54+
Keep replicaCount=1 unless you intentionally disable or externalize scraping.
55+
Pumperly starts in-process scrapers inside the web container.
Lines changed: 148 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,148 @@
1+
{{/*
2+
Expand the name of the chart.
3+
*/}}
4+
{{- define "pumperly.name" -}}
5+
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
6+
{{- end }}
7+
8+
{{/*
9+
Create a default fully qualified app name.
10+
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
11+
If release name contains chart name it will be used as a full name.
12+
*/}}
13+
{{- define "pumperly.fullname" -}}
14+
{{- if .Values.fullnameOverride }}
15+
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
16+
{{- else }}
17+
{{- $name := default .Chart.Name .Values.nameOverride }}
18+
{{- if contains $name .Release.Name }}
19+
{{- .Release.Name | trunc 63 | trimSuffix "-" }}
20+
{{- else }}
21+
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" }}
22+
{{- end }}
23+
{{- end }}
24+
{{- end }}
25+
26+
{{/*
27+
Create chart name and version as used by the chart label.
28+
*/}}
29+
{{- define "pumperly.chart" -}}
30+
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
31+
{{- end }}
32+
33+
{{/*
34+
Common labels
35+
*/}}
36+
{{- define "pumperly.labels" -}}
37+
helm.sh/chart: {{ include "pumperly.chart" . }}
38+
{{ include "pumperly.selectorLabels" . }}
39+
{{- if .Chart.AppVersion }}
40+
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
41+
{{- end }}
42+
app.kubernetes.io/managed-by: {{ .Release.Service }}
43+
{{- end }}
44+
45+
{{/*
46+
Selector labels
47+
*/}}
48+
{{- define "pumperly.selectorLabels" -}}
49+
app.kubernetes.io/name: {{ include "pumperly.name" . }}
50+
app.kubernetes.io/instance: {{ .Release.Name }}
51+
{{- end }}
52+
53+
{{/*
54+
Selector labels for the web application.
55+
*/}}
56+
{{- define "pumperly.webSelectorLabels" -}}
57+
{{ include "pumperly.selectorLabels" . }}
58+
app.kubernetes.io/component: web
59+
{{- end }}
60+
61+
{{/*
62+
PostGIS selector labels
63+
*/}}
64+
{{- define "pumperly.postgis.selectorLabels" -}}
65+
app.kubernetes.io/name: {{ include "pumperly.name" . }}-postgis
66+
app.kubernetes.io/instance: {{ .Release.Name }}
67+
{{- end }}
68+
69+
{{/*
70+
Valhalla selector labels
71+
*/}}
72+
{{- define "pumperly.valhalla.selectorLabels" -}}
73+
app.kubernetes.io/name: {{ include "pumperly.name" . }}-valhalla
74+
app.kubernetes.io/instance: {{ .Release.Name }}
75+
{{- end }}
76+
77+
{{/*
78+
Photon selector labels
79+
*/}}
80+
{{- define "pumperly.photon.selectorLabels" -}}
81+
app.kubernetes.io/name: {{ include "pumperly.name" . }}-photon
82+
app.kubernetes.io/instance: {{ .Release.Name }}
83+
{{- end }}
84+
85+
{{/*
86+
Create the name of the service account to use
87+
*/}}
88+
{{- define "pumperly.serviceAccountName" -}}
89+
{{- if .Values.serviceAccount.create }}
90+
{{- default (include "pumperly.fullname" .) .Values.serviceAccount.name }}
91+
{{- else }}
92+
{{- default "default" .Values.serviceAccount.name }}
93+
{{- end }}
94+
{{- end }}
95+
96+
{{/*
97+
PostGIS fully qualified name
98+
*/}}
99+
{{- define "pumperly.postgis.fullname" -}}
100+
{{- printf "%s-postgis" (include "pumperly.fullname" .) }}
101+
{{- end }}
102+
103+
{{/*
104+
Valhalla fully qualified name
105+
*/}}
106+
{{- define "pumperly.valhalla.fullname" -}}
107+
{{- printf "%s-valhalla" (include "pumperly.fullname" .) }}
108+
{{- end }}
109+
110+
{{/*
111+
Photon fully qualified name
112+
*/}}
113+
{{- define "pumperly.photon.fullname" -}}
114+
{{- printf "%s-photon" (include "pumperly.fullname" .) }}
115+
{{- end }}
116+
117+
{{/*
118+
Secret name
119+
*/}}
120+
{{- define "pumperly.secretName" -}}
121+
{{- if .Values.existingSecret -}}
122+
{{- .Values.existingSecret -}}
123+
{{- else -}}
124+
{{- printf "%s-secret" (include "pumperly.fullname" .) }}
125+
{{- end -}}
126+
{{- end }}
127+
128+
{{/*
129+
Database host
130+
*/}}
131+
{{- define "pumperly.databaseHost" -}}
132+
{{- if .Values.postgis.enabled -}}
133+
{{- include "pumperly.postgis.fullname" . -}}
134+
{{- else -}}
135+
{{- .Values.externalDatabase.host -}}
136+
{{- end -}}
137+
{{- end -}}
138+
139+
{{/*
140+
Database port
141+
*/}}
142+
{{- define "pumperly.databasePort" -}}
143+
{{- if .Values.postgis.enabled -}}
144+
5432
145+
{{- else -}}
146+
{{- .Values.externalDatabase.port -}}
147+
{{- end -}}
148+
{{- end -}}

0 commit comments

Comments
 (0)