From 271910904ea35cdab28d5084f266d59ba7e30ddc Mon Sep 17 00:00:00 2001
From: "Dominik.Sigmund" <dominik.sigmund@br.de>
Date: Tue, 9 Jul 2024 13:24:45 +0200
Subject: [PATCH] Added k8s files

---
 commands/init.go                              | 97 +++++++++++++++++--
 templates/dockerignore.tmpl                   | 33 +++++++
 templates/gitignore.tmpl                      | 28 ++++++
 .../k8s/deployment.mysql.template.yaml.tmpl   | 57 +++++++++++
 .../deployment.postgres.template.yaml.tmpl    | 57 +++++++++++
 .../k8s/persistentVolume.template.yaml.tmpl   | 15 +++
 .../persistentVolumeClaim.template.yaml.tmpl  | 17 ++++
 templates/k8s/service.template.yaml.tmpl      | 19 ++++
 templates/templates.go                        |  6 +-
 9 files changed, 320 insertions(+), 9 deletions(-)
 create mode 100644 templates/dockerignore.tmpl
 create mode 100644 templates/gitignore.tmpl
 create mode 100644 templates/k8s/deployment.mysql.template.yaml.tmpl
 create mode 100644 templates/k8s/deployment.postgres.template.yaml.tmpl
 create mode 100644 templates/k8s/persistentVolume.template.yaml.tmpl
 create mode 100644 templates/k8s/persistentVolumeClaim.template.yaml.tmpl
 create mode 100644 templates/k8s/service.template.yaml.tmpl

diff --git a/commands/init.go b/commands/init.go
index 5c7ef18..4042cf2 100644
--- a/commands/init.go
+++ b/commands/init.go
@@ -43,19 +43,36 @@ func InitProject(name string, dbType string) {
 	// Create LICENSE.md file from template
 	createLicenseFile(slug, name)
 
+	// Create .gitignore file from template
+	createGitignoreFile(slug)
+
+	// Create .dockerignore file from template
+	createDockerignoreFile(slug)
+
+
+	
+
+	// Create k8s/persistentvolumeclaim.template.yaml file from template
+	createK8sPersistentVolumeFile(slug)
+
+	// Create k8s/persistentvolumeclaim.template.yaml file from template
+	createK8sPersistentVolumeClaimFile(slug)
+
+	// Create k8s/service.template.yaml file from template
+	createK8sServiceFile(slug)
+
+	// Create k8s/deployment.template.yaml file from template based on dbType
+	createK8sDeploymentFile(slug, dbType)
+
 	// TODO: copy base files from https://gitlab.ard.de/br/buzzboard/database/-/tree/develop?ref_type=heads
 	/*
-		- .gitignore
-		- .dockerignore
 		- .sqlfluff (by database type)
 		- Containerfile (by database type)
 		- README.md
+		- CONTRIBUTING.md
+		- CHANGELOG.md
 		- import-sql.sh (by database type)
 		- .gilab-ci.yml (by database type) (also import tests from blessing of the day)
-		- k8s/deployment.template.yaml
-		- k8s/service.template.yaml
-		- k8s/persistentVolume.template.yaml
-		- k8s/persistentVolumeClaim.template.yaml
 		- sql/database.sql (by database type)
 	*/
 
@@ -140,6 +157,74 @@ func createLicenseFile(projectDir, projectName string) {
 	}
 }
 
+// createGitignoreFile creates the .gitignore file from template
+func createGitignoreFile(projectDir string) {
+	err := templates.CreateFileFromTemplate(projectDir, "", ".gitignore", "gitignore", nil)
+	if err != nil {
+		fmt.Printf("Error creating .gitignore file: %v\n", err)
+	} else {
+		fmt.Printf("Created file: %s/.gitignore\n", projectDir)
+	}
+}
+
+// createDockerignoreFile creates the .dockerignore file from template
+func createDockerignoreFile(projectDir string) {
+	err := templates.CreateFileFromTemplate(projectDir, "", ".dockerignore", ".dockerignore", nil)
+	if err != nil {
+		fmt.Printf("Error creating .dockerignore file: %v\n", err)
+	} else {
+		fmt.Printf("Created file: %s/.dockerignore\n", projectDir)
+	}
+}
+
+// createK8sPersistentVolumeClaimFile creates the k8s/persistentVolume.template.yaml file from template
+func createK8sPersistentVolumeFile(projectDir string) {
+
+	err := templates.CreateFileFromTemplate(projectDir, "k8s", "persistentVolume.template.yaml", "k8s/persistentVolume.template.yaml", nil)
+	if err != nil {
+		fmt.Printf("Error creating k8s/persistentVolume.template.yaml file: %v\n", err)
+	} else {
+		fmt.Printf("Created file: %s/k8s/persistentVolume.template.yaml\n", projectDir)
+	}
+}
+
+// createK8sPersistentVolumeClaimFile creates the k8s/persistentVolumeClaim.template.yaml file from template
+func createK8sPersistentVolumeClaimFile(projectDir string) {
+
+	err := templates.CreateFileFromTemplate(projectDir, "k8s", "persistentVolumeClaim.template.yaml", "k8s/persistentVolumeClaim.template.yaml", nil)
+	if err != nil {
+		fmt.Printf("Error creating k8s/persistentVolumeClaim.template.yaml file: %v\n", err)
+	} else {
+		fmt.Printf("Created file: %s/k8s/persistentVolumeClaim.template.yaml\n", projectDir)
+	}
+}
+
+// createK8sPerviceFile creates the k8s/service.template.yaml file from template
+func createK8sServiceFile(projectDir string) {
+
+	err := templates.CreateFileFromTemplate(projectDir, "k8s", "service.template.yaml", "k8s/service.template.yaml", nil)
+	if err != nil {
+		fmt.Printf("Error creating k8s/service.template.yaml file: %v\n", err)
+	} else {
+		fmt.Printf("Created file: %s/k8s/service.template.yaml\n", projectDir)
+	}
+}
+
+// createK8sDeploymentFile creates the k8s/deployment.template.yaml file from the appropriate template
+func createK8sDeploymentFile(projectDir, dbType string) {
+	templateFile := "k8s/deployment.mysql.template.yaml"
+	if dbType == "postgres" {
+	templateFile = "k8s/deployment.postgres.template.yaml"
+	}
+	
+	err := templates.CreateFileFromTemplate(projectDir, "k8s", "deployment.template.yaml", templateFile, nil)
+	if err != nil {
+		fmt.Printf("Error creating k8s/deployment.template.yaml file: %v\n", err)
+	} else {
+		fmt.Printf("Created file: %s/k8s/deployment.template.yaml\n", projectDir)
+	}
+}
+
 // Help returns the help information for the init command
 func InitHelp() string {
 	return "init [name] [--type mysql|postgres] : Create a new project with the specified name and database type."
diff --git a/templates/dockerignore.tmpl b/templates/dockerignore.tmpl
new file mode 100644
index 0000000..1e52152
--- /dev/null
+++ b/templates/dockerignore.tmpl
@@ -0,0 +1,33 @@
+# .dockerignore
+
+# Node modules
+node_modules/
+
+# Logs
+logs
+*.log
+
+# Environment files
+.env
+
+# Database files
+*.dbml
+
+# Kubernetes files
+k8s/
+
+# Docs
+README.md
+LICENSE.md
+CHANGELOG.md
+CONTRIBUTING.md
+
+# Temporary files
+tmp/
+temp/
+*.tmp
+*.temp
+
+# Build output
+dist/
+build/
\ No newline at end of file
diff --git a/templates/gitignore.tmpl b/templates/gitignore.tmpl
new file mode 100644
index 0000000..61dbfb8
--- /dev/null
+++ b/templates/gitignore.tmpl
@@ -0,0 +1,28 @@
+# .gitignore
+
+# Node modules
+node_modules/
+
+# Logs
+logs
+*.log
+npm-debug.log*
+yarn-debug.log*
+yarn-error.log*
+
+# Environment files
+.env
+
+# Temporary files
+tmp/
+temp/
+*.tmp
+*.temp
+
+# IDE specific files
+.vscode/
+.idea/
+
+# Build output
+dist/
+build/
\ No newline at end of file
diff --git a/templates/k8s/deployment.mysql.template.yaml.tmpl b/templates/k8s/deployment.mysql.template.yaml.tmpl
new file mode 100644
index 0000000..b0cf605
--- /dev/null
+++ b/templates/k8s/deployment.mysql.template.yaml.tmpl
@@ -0,0 +1,57 @@
+apiVersion: apps/v1
+kind: Deployment
+metadata:
+  name: ${CI_PROJECT_NAME}
+  namespace: ${K8S_NAMESPACE}
+  labels:
+    app.kubernetes.io/name: ${CI_PROJECT_NAME}
+    app.kubernetes.io/version: ${VERSION}
+    app.kubernetes.io/managed-by: cicd
+    app.kubernetes.io/created-by: gitlab
+spec:
+  replicas: ${REPLICAS}
+  strategy:
+    type: RollingUpdate
+  selector:
+    matchLabels:
+      app.kubernetes.io/name: ${CI_PROJECT_NAME}
+      app.kubernetes.io/managed-by: cicd
+      app.kubernetes.io/created-by: gitlab
+  template:
+    metadata:
+      name: ${CI_PROJECT_NAME}_
+      namespace: ${K8S_NAMESPACE}
+      labels:
+        app.kubernetes.io/name: ${CI_PROJECT_NAME}
+        app.kubernetes.io/version: ${VERSION}
+        app.kubernetes.io/managed-by: cicd
+        app.kubernetes.io/created-by: gitlab
+    spec:
+      volumes:
+        - name: ${CI_PROJECT_NAME}
+          persistentVolumeClaim:
+            claimName: ${CI_PROJECT_NAME}
+      containers:
+      - name: ${CI_PROJECT_NAME}
+        image: ${CI_REGISTRY_IMAGE}:${TAG}
+        imagePullPolicy: Always
+        ports:
+          - containerPort: ${PORT}
+        volumeMounts:
+          - name: ${CI_PROJECT_NAME}
+            mountPath: /var/lib/mysql
+        livenessProbe:
+          exec:
+            command:
+            - bash
+            - -c
+            - mysqladmin -u ${DB_USER} -p${DB_PASSWORD} ping
+          periodSeconds: 10
+        startupProbe:
+          exec:
+            command:
+            - bash
+            - -c
+            - mysql -u ${DB_USER} -p${DB_PASSWORD} -e "SELECT 1"
+          periodSeconds: 10
+          failureThreshold: 60 # total 60x10s = 600s = 10min to initialize
\ No newline at end of file
diff --git a/templates/k8s/deployment.postgres.template.yaml.tmpl b/templates/k8s/deployment.postgres.template.yaml.tmpl
new file mode 100644
index 0000000..8b21521
--- /dev/null
+++ b/templates/k8s/deployment.postgres.template.yaml.tmpl
@@ -0,0 +1,57 @@
+apiVersion: apps/v1
+kind: Deployment
+metadata:
+  name: ${CI_PROJECT_NAME}
+  namespace: ${K8S_NAMESPACE}
+  labels:
+    app.kubernetes.io/name: ${CI_PROJECT_NAME}
+    app.kubernetes.io/version: ${VERSION}
+    app.kubernetes.io/managed-by: cicd
+    app.kubernetes.io/created-by: gitlab
+spec:
+  replicas: ${REPLICAS}
+  strategy:
+    type: RollingUpdate
+  selector:
+    matchLabels:
+      app.kubernetes.io/name: ${CI_PROJECT_NAME}
+      app.kubernetes.io/managed-by: cicd
+      app.kubernetes.io/created-by: gitlab
+  template:
+    metadata:
+      name: ${CI_PROJECT_NAME}
+      namespace: ${K8S_NAMESPACE}
+      labels:
+        app.kubernetes.io/name: ${CI_PROJECT_NAME}
+        app.kubernetes.io/version: ${VERSION}
+        app.kubernetes.io/managed-by: cicd
+        app.kubernetes.io/created-by: gitlab
+    spec:
+      volumes:
+        - name: ${CI_PROJECT_NAME}
+          persistentVolumeClaim:
+            claimName: ${CI_PROJECT_NAME}
+      containers:
+      - name: ${CI_PROJECT_NAME}
+        image: ${CI_REGISTRY_IMAGE}:${TAG}
+        imagePullPolicy: Always
+        ports:
+          - containerPort: ${PORT}
+        volumeMounts:
+          - name: ${CI_PROJECT_NAME}
+            mountPath: /var/lib/postgresql/data
+        livenessProbe:
+          exec:
+            command:
+            - bash
+            - -c
+            - pg_isready -U ${DB_USER}
+          periodSeconds: 10
+        startupProbe:
+          exec:
+            command:
+            - bash
+            - -c
+            - pg_isready -U ${DB_USER}
+          periodSeconds: 10
+          failureThreshold: 60 # total 60x10s = 600s = 10min to initialize
\ No newline at end of file
diff --git a/templates/k8s/persistentVolume.template.yaml.tmpl b/templates/k8s/persistentVolume.template.yaml.tmpl
new file mode 100644
index 0000000..d5ee89d
--- /dev/null
+++ b/templates/k8s/persistentVolume.template.yaml.tmpl
@@ -0,0 +1,15 @@
+apiVersion: v1
+kind: PersistentVolume
+metadata:
+  name: ${CI_PROJECT_NAME}
+spec:
+  storageClassName: ${CI_PROJECT_NAME}
+  capacity:
+    storage: 100Gi
+  accessModes:
+    - ReadWriteMany
+  nfs:
+    server: ${NFS_SERVER}
+    path: /${NFS_VOLUME}/${NFS_PATH}
+  mountOptions:
+    - nfsvers=3.0
\ No newline at end of file
diff --git a/templates/k8s/persistentVolumeClaim.template.yaml.tmpl b/templates/k8s/persistentVolumeClaim.template.yaml.tmpl
new file mode 100644
index 0000000..d4844ca
--- /dev/null
+++ b/templates/k8s/persistentVolumeClaim.template.yaml.tmpl
@@ -0,0 +1,17 @@
+apiVersion: v1
+kind: PersistentVolumeClaim
+metadata:
+  labels:
+    app.kubernetes.io/name: ${CI_PROJECT_NAME}
+    app.kubernetes.io/managed-by: cicd
+    app.kubernetes.io/created-by: gitlab
+  name: ${CI_PROJECT_NAME}
+  namespace: ${NAMESPACE}
+spec:
+  accessModes:
+  - ReadWriteMany
+  resources:
+    requests:
+      storage: ${NFS_SIZE}Gi
+  volumeName: ${CI_PROJECT_NAME}
+  storageClassName: ${CI_PROJECT_NAME}
\ No newline at end of file
diff --git a/templates/k8s/service.template.yaml.tmpl b/templates/k8s/service.template.yaml.tmpl
new file mode 100644
index 0000000..ac58ef4
--- /dev/null
+++ b/templates/k8s/service.template.yaml.tmpl
@@ -0,0 +1,19 @@
+apiVersion: v1
+kind: Service
+metadata:
+  name: ${CI_PROJECT_NAME}
+  namespace: ${K8S_NAMESPACE}
+  labels:
+    app.kubernetes.io/name: ${CI_PROJECT_NAME}
+    app.kubernetes.io/managed-by: cicd
+    app.kubernetes.io/created-by: gitlab
+spec:
+  ports:
+  - port: ${PORT}
+    protocol: TCP
+    targetPort: ${PORT}
+    name: ${CI_PROJECT_NAME}
+  selector:
+    app.kubernetes.io/name: ${CI_PROJECT_NAME}
+    app.kubernetes.io/managed-by: cicd
+    app.kubernetes.io/created-by: gitlab
\ No newline at end of file
diff --git a/templates/templates.go b/templates/templates.go
index e6796ad..e3bd827 100644
--- a/templates/templates.go
+++ b/templates/templates.go
@@ -8,7 +8,7 @@ import (
 	"fmt"
 )
 
-//go:embed *.tmpl
+//go:embed *.tmpl k8s/*.tmpl
 var templateFS embed.FS
 
 // LoadTemplate loads a template from the embedded filesystem
@@ -21,13 +21,13 @@ func LoadTemplate(tmplName string) (*template.Template, error) {
 }
 
 // CreateFileFromTemplate creates a file from a template
-func CreateFileFromTemplate(bookDir, subDir, filename, tmplName string, data interface{}) error {
+func CreateFileFromTemplate(baseDir, subDir, filename, tmplName string, data interface{}) error {
 	tmpl, err := LoadTemplate(tmplName)
 	if err != nil {
 		return err
 	}
 
-	filePath := filepath.Join(bookDir, subDir, filename)
+	filePath := filepath.Join(baseDir, subDir, filename)
 	file, err := os.Create(filePath)
 	if err != nil {
 		return err
-- 
GitLab