From 7a2b237376c1cf90b87ddfbe6adcc1c8b3d29070 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 11:13:20 +0100 Subject: [PATCH 01/21] Update: Added additional external secrets configs --- .github/workflows/iac.yml | 4 ---- 1 file changed, 4 deletions(-) delete mode 100644 .github/workflows/iac.yml diff --git a/.github/workflows/iac.yml b/.github/workflows/iac.yml deleted file mode 100644 index 7fc7e45..0000000 --- a/.github/workflows/iac.yml +++ /dev/null @@ -1,4 +0,0 @@ -name: iac.yml -on: - -jobs: From 18027290a0ae74596bfc93224a22617cbd2b9aae Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 11:13:26 +0100 Subject: [PATCH 02/21] Update: Added additional external secrets configs --- .../key-vault-external-secrets.yaml | 61 ++++++++++++++++++- .../mtls-lockdown-peer-authentication.yaml | 2 +- .../storage-service-deployment-v1.0.yaml | 4 +- .../user-service-deployment-v1.0.yaml | 4 +- infrastructure/prod/terraform/main.tf | 43 +++++++------ .../service/StorageService.java | 2 +- .../src/main/resources/application.yaml | 7 ++- .../src/main/resources/application.yaml | 2 +- 8 files changed, 94 insertions(+), 31 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index 7c1fecd..aa609f4 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -56,7 +56,7 @@ spec: .dockerconfigjson: | { "auths": { - "acrdevopsprojectprod.azurecr.io": { + "{{ .token }}.azurecr.io": { # Token username is the same as ACR name "username": "{{ .token }}", "password": "{{ .password }}" } @@ -68,4 +68,61 @@ spec: key: secret/aks-acr-token - secretKey: password remoteRef: - key: secret/aks-acr-password \ No newline at end of file + key: secret/aks-acr-password +--- +apiVersion: external-secrets.io/v1 +kind: ExternalSecret +metadata: + name: postgresql-credentials + namespace: prod +spec: + secretStoreRef: + kind: ClusterSecretStore + name: azure-cluster-secret-store + refreshPolicy: Periodic + refreshInterval: 0h5m0s + target: + name: postgresql-credentials + creationPolicy: Owner + template: + data: + config.yml: | + postgresql: + uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require # Complete URI for JDBC with TLS required + username: {{ .username }} + password: {{ .password }} + data: + - secretKey: uri + remoteRef: + key: secret/postgresql-uri + - secretKey: username + remoteRef: + key: secret/postgresql-username + - secretKey: password + remoteRef: + key: secret/postgresql-password +--- +apiVersion: external-secrets.io/v1 +kind: ExternalSecret +metadata: + name: cloudflare-r2-credentials + namespace: prod +spec: + secretStoreRef: + kind: ClusterSecretStore + name: azure-cluster-secret-store + refreshPolicy: Periodic + refreshInterval: 0h5m0s + target: + name: cloudflare-r2-credentials + creationPolicy: Owner + data: + - secretKey: apiUri + remoteRef: + key: secret/cloudflare-r2-api-uri + - secretKey: accessKeyId + remoteRef: + key: secret/cloudflare-r2-account-id + - secretKey: secretAccessKey + remoteRef: + key: secret/cloudflare-api-token \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/istio-manifests/mtls-lockdown-peer-authentication.yaml b/infrastructure/prod/kubernetes/istio-manifests/mtls-lockdown-peer-authentication.yaml index 131bc99..e86cadf 100644 --- a/infrastructure/prod/kubernetes/istio-manifests/mtls-lockdown-peer-authentication.yaml +++ b/infrastructure/prod/kubernetes/istio-manifests/mtls-lockdown-peer-authentication.yaml @@ -5,4 +5,4 @@ metadata: namespace: istio-system spec: mtls: - mode: PERMISSIVE # Lock down workloads in all namespaces to prioritise accept mTLS traffic \ No newline at end of file + mode: STRICT # Lock down workloads in all namespaces to prioritise accept mTLS traffic \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml index c89c60c..41895c5 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml @@ -22,7 +22,7 @@ spec: - name: azurecr-credentials containers: - name: storage-service - image: storage-service:dev + image: acrdevopsprojectprod.azurecr.io/storage-service:dev imagePullPolicy: IfNotPresent ports: - containerPort: 8080 @@ -46,4 +46,4 @@ spec: initialDelaySeconds: 15 periodSeconds: 10 serviceAccountName: storage-service - restartPolicy: Always \ No newline at end of file + restartPolicy: OnFailure \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml index 7d017f6..4e4d2a0 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml @@ -22,7 +22,7 @@ spec: - name: azurecr-credentials containers: - name: user-service - image: user-service:dev + image: acrdevopsprojectprod.azurecr.io/user-service:dev imagePullPolicy: IfNotPresent ports: - containerPort: 8080 @@ -46,4 +46,4 @@ spec: initialDelaySeconds: 15 periodSeconds: 10 serviceAccountName: user-service - restartPolicy: Always \ No newline at end of file + restartPolicy: OnFailure \ No newline at end of file diff --git a/infrastructure/prod/terraform/main.tf b/infrastructure/prod/terraform/main.tf index 47f6bb3..8d47b67 100644 --- a/infrastructure/prod/terraform/main.tf +++ b/infrastructure/prod/terraform/main.tf @@ -35,7 +35,7 @@ resource "cloudflare_r2_custom_domain" "devops_r2_custom_domain" { domain = "r2storage-${local.env}.kacperklimas.com" enabled = true zone_id = var.cloudflare_dns_zone_id - min_tls = "1.2" + min_tls = "1.2" # What's interesting R2 resource block use TLS 1.0 as default minimum version which is not recommended and can cause major security issues, so we need to change to TLS 1.2 } /* AZURE */ @@ -200,13 +200,6 @@ module "azure_management_vnet" { id = module.azure_management_vnet_nsg.resource_id } } - # "dbsubnet" = { - # name = "DatabaseInstancesSubnet" - # address_prefixes = ["10.1.2.0/24"] - # network_security_group = { - # id = module.azure_management_vnet_nsg.resource_id - # } - # } } tags = var.azure_application_tags } @@ -584,12 +577,20 @@ module "devops_key_vault" { description = "KeyVaultDefaultClient" } } - secrets = { # Create secret for Kubernetes external dns and cert manager + secrets = { # Create secret for Kubernetes external dns and cert manager whole workload + cloudflare_r2_api_uri = { + name = "cloudflare-r2-api-uri" + tags = var.azure_application_tags + } + cloudflare_r2_account_id = { + name = "cloudflare-r2-account-id" + tags = var.azure_application_tags + } cloudflare_api_token = { name = "cloudflare-api-token" tags = var.azure_application_tags } - aks_registry_login = { + aks_registry_token = { name = "aks-acr-token" tags = var.azure_application_tags } @@ -601,8 +602,8 @@ module "devops_key_vault" { name = "postgresql-uri" tags = var.azure_application_tags } - postgresql_user = { - name = "postgresql-user" + postgresql_username = { + name = "postgresql-username" tags = var.azure_application_tags } postgresql_password = { @@ -611,12 +612,14 @@ module "devops_key_vault" { } } secrets_value = { - cloudflare_api_token = var.cloudflare_api_token - aks_registry_login = module.azure_container_registry.name - aks_registry_password = local.container_registry_aks_password - postgresql_uri = data.azurerm_postgresql_flexible_server.devops_postgresql.fqdn - postgresql_user = data.azurerm_postgresql_flexible_server.devops_postgresql.administrator_login - postgresql_password = random_password.postgresql_admin_password.result + cloudflare_r2_api_uri = "https://${cloudflare_r2_custom_domain.devops_r2_custom_domain.domain}/${cloudflare_r2_bucket.devops_r2_bucket.name}" + cloudflare_r2_account_id = var.cloudflare_account_id + cloudflare_api_token = var.cloudflare_api_token + aks_registry_token = module.azure_container_registry.name + aks_registry_password = local.container_registry_aks_password + postgresql_uri = data.azurerm_postgresql_flexible_server.devops_postgresql.fqdn + postgresql_username = data.azurerm_postgresql_flexible_server.devops_postgresql.administrator_login + postgresql_password = random_password.postgresql_admin_password.result } tags = var.azure_application_tags } @@ -628,7 +631,7 @@ module "devops_postgresql" { name = "${module.azure_naming.postgresql_server.name}-${local.env}" resource_group_name = module.azure_resource_group.name location = var.azure_region - server_version = "16" # Postgresql 18 + server_version = "16" # Postgresql 16 sku_name = "GP_Standard_D2ds_v4" # 2 vCores, 8 GiB memory, 3750 max iops for Server VM. Depends on Region and current availability storage_mb = "32768" # 32 GB on SSD Disk authentication = { @@ -641,7 +644,7 @@ module "devops_postgresql" { high_availability = { mode = "SameZone" } - zone = "1" # Need to choose AZ for correct provisioning + zone = "1" # Need to choose AZ for correct provisioning databases = { devops = { name = "devops" diff --git a/storage-service/src/main/java/com/devops/storageservice/service/StorageService.java b/storage-service/src/main/java/com/devops/storageservice/service/StorageService.java index 6d86aa2..6e71dbf 100644 --- a/storage-service/src/main/java/com/devops/storageservice/service/StorageService.java +++ b/storage-service/src/main/java/com/devops/storageservice/service/StorageService.java @@ -13,7 +13,7 @@ @RequiredArgsConstructor public class StorageService { - @Qualifier("BlobStorage") + @Qualifier("R2Storage") private final StorageRepository storageRepository; public FileUploadResponseDto fileUploadRequest(FileUploadRequestDto fileUploadRequestDto) { diff --git a/storage-service/src/main/resources/application.yaml b/storage-service/src/main/resources/application.yaml index 87eefed..d7a9597 100644 --- a/storage-service/src/main/resources/application.yaml +++ b/storage-service/src/main/resources/application.yaml @@ -3,15 +3,18 @@ spring: name: "storage-service" cloud: aws: + credentials: + access-key: "${BUCKET_ACCESS_KEY}:kacperkacper" + secret-key: "${BUCKET_SECRET_KEY}:kacperkacper" s3: endpoint: "${BUCKET_ENDPOINT:http://localhost:9000}" - region: "us-east-1" # Auto region for Minio and R2 + region: "${BUCKET_REGION}:us-east-1" # Auto region for Minio and R2 rabbitmq: username: "${RABBITMQ_USERNAME:kacper}" password: "${RABBITMQ_PASSWORD:kacper}" + virtual-host: "${RABBITMQ_VHOST:rabbitmq}" host: "${RABBITMQ_HOST:localhost}" port: "${RABBITMQ_PORT:5672}" - virtual-host: "${RABBITMQ_VHOST:rabbitmq}" template: retry: enabled: true diff --git a/user-service/src/main/resources/application.yaml b/user-service/src/main/resources/application.yaml index 82ef30b..37d9cff 100644 --- a/user-service/src/main/resources/application.yaml +++ b/user-service/src/main/resources/application.yaml @@ -4,7 +4,7 @@ spring: datasource: username: "${POSTGRESQL_USERNAME:kacper}" password: "${POSTGRESQL_PASSWORD:kacper}" - url: "${POSTGRESQL_URL:jdbc:postgresql://localhost/devops}" + url: "${POSTGRESQL_URI:jdbc:postgresql://localhost/devops}" driver-class-name: org.postgresql.Driver jpa: hibernate: From 6dd3c719268120cb38988d825c780b76a91e1247 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 11:17:33 +0100 Subject: [PATCH 03/21] Hotfix: Comment --- .../key-vault-external-secrets.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index aa609f4..a896e4d 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -85,10 +85,10 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: + data: # Complete URI for JDBC with TLS required config.yml: | postgresql: - uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require # Complete URI for JDBC with TLS required + uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require username: {{ .username }} password: {{ .password }} data: From 294b803b4a58a4d7b34e47f200e1aedc29cd8ace Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 11:27:05 +0100 Subject: [PATCH 04/21] Hotfix: Comment --- .../key-vault-external-secrets.yaml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index a896e4d..5c89802 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -11,7 +11,7 @@ spec: refreshInterval: 0h5m0s target: name: cloudflare-api-token-secret - creationPolicy: Owner # Creates Kubernetes secret if ExternalSecret created + creationPolicy: Owner # Creates Kubernetes secret if ExternalSecret created data: - secretKey: api-token remoteRef: @@ -53,10 +53,10 @@ spec: template: type: kubernetes.io/dockerconfigjson data: - .dockerconfigjson: | + .dockerconfigjson: | # Token username is the same as ACR name { "auths": { - "{{ .token }}.azurecr.io": { # Token username is the same as ACR name + "{{ .token }}.azurecr.io": { "username": "{{ .token }}", "password": "{{ .password }}" } @@ -85,8 +85,8 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: # Complete URI for JDBC with TLS required - config.yml: | + data: + config.yml: | # Complete URI for JDBC with TLS required postgresql: uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require username: {{ .username }} From ca54fe51b3961cf8ac438bc4a05e9fc62434941f Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 17:03:26 +0100 Subject: [PATCH 05/21] Update: Configured Kubernetes deployments --- infrastructure/dev/docker-compose.yaml | 2 +- .../key-vault-external-secrets.yaml | 11 ++++----- .../storage-service-deployment-v1.0.yaml | 24 +++++++++++++++++-- .../user-service-deployment-v1.0.yaml | 24 +++++++++++++++++-- 4 files changed, 50 insertions(+), 11 deletions(-) diff --git a/infrastructure/dev/docker-compose.yaml b/infrastructure/dev/docker-compose.yaml index bc16bb3..a9a53ae 100644 --- a/infrastructure/dev/docker-compose.yaml +++ b/infrastructure/dev/docker-compose.yaml @@ -59,7 +59,7 @@ services: environment: SERVER_PORT: 8080 RABBITMQ_HOST: rabbitmq - POSTGRESQL_URL: jdbc:postgresql://postgresql/devops + POSTGRESQL_URI: jdbc:postgresql://postgresql/devops networks: - backend-network - db-network diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index 5c89802..48358bf 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -85,12 +85,11 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: - config.yml: | # Complete URI for JDBC with TLS required - postgresql: - uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require - username: {{ .username }} - password: {{ .password }} + data: # Complete URI for JDBC with TLS required + postgresql: + uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require + username: {{ .username }} + password: {{ .password }} data: - secretKey: uri remoteRef: diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml index 41895c5..7c14409 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml @@ -24,6 +24,26 @@ spec: - name: storage-service image: acrdevopsprojectprod.azurecr.io/storage-service:dev imagePullPolicy: IfNotPresent + env: + - name: SERVER_PORT + value: "8080" + - name: RABBITMQ_HOST + value: devops-project-cluster.rabbitmq-system.svc.cluster.local + - name: BUCKET_ENDPOINT + valueFrom: + secretKeyRef: + name: cloudflare-r2-credentials + key: apiUri + - name: BUCKET_ACCESS_KEY + valueFrom: + secretKeyRef: + name: cloudflare-r2-credentials + key: accessKeyId + - name: BUCKET_SECRET_KEY + valueFrom: + secretKeyRef: + name: cloudflare-r2-credentials + key: secretAccessKey ports: - containerPort: 8080 protocol: TCP @@ -45,5 +65,5 @@ spec: port: 8080 initialDelaySeconds: 15 periodSeconds: 10 - serviceAccountName: storage-service - restartPolicy: OnFailure \ No newline at end of file + restartPolicy: Always + serviceAccountName: storage-service \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml index 4e4d2a0..8c36ec3 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml @@ -24,6 +24,26 @@ spec: - name: user-service image: acrdevopsprojectprod.azurecr.io/user-service:dev imagePullPolicy: IfNotPresent + env: + - name: SERVER_PORT + value: "8080" + - name: RABBITMQ_HOST + value: devops-project-cluster.rabbitmq-system.svc.cluster.local + - name: POSTGRESQL_URI + valueFrom: + secretKeyRef: + name: postgresql-credentials + key: postgresql.uri + - name: POSTGRESQL_USERNAME + valueFrom: + secretKeyRef: + name: postgresql-credentials + key: postgresql.username + - name: POSTGRESQL_PASSWORD + valueFrom: + secretKeyRef: + name: postgresql-credentials + key: postgresql.password ports: - containerPort: 8080 protocol: TCP @@ -45,5 +65,5 @@ spec: port: 8080 initialDelaySeconds: 15 periodSeconds: 10 - serviceAccountName: user-service - restartPolicy: OnFailure \ No newline at end of file + restartPolicy: Always + serviceAccountName: user-service \ No newline at end of file From e0b426fae4aad613e5903880ac745f2c5535a0da Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 17:05:54 +0100 Subject: [PATCH 06/21] Hotfix: External secrets hotfix --- .../key-vault-external-secrets.yaml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index 48358bf..fa5b919 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -85,8 +85,8 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: # Complete URI for JDBC with TLS required - postgresql: + data: + postgresql: | # Complete URI for JDBC with TLS required uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require username: {{ .username }} password: {{ .password }} From a235479661b54cd20e03954bb0e5447e031a4c95 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 18:19:41 +0100 Subject: [PATCH 07/21] Update: Added Kubernetes RBAC for microservices --- .../storage-service-rbac.yaml | 23 +++++++++++++++++++ .../user-service-rbac.yaml | 23 +++++++++++++++++++ 2 files changed, 46 insertions(+) create mode 100644 infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml create mode 100644 infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml new file mode 100644 index 0000000..b4c53b7 --- /dev/null +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml @@ -0,0 +1,23 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: Role +metadata: + name: storage-service-read-secrets + namespace: prod +rules: + - apiGroups: [ "v1" ] + resources: [ "secrets" ] + verbs: [get, list] +--- +apiVersion: rbac.authorization.k8s.io/v1 +kind: RoleBinding +metadata: + name: read-secrets + namespace: prod +subjects: + - apiGroup: rbac.authorization.k8s.io + kind: ServiceAccount + name: storage-service +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: Role + name: storage-service-read-secrets \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml new file mode 100644 index 0000000..24c0047 --- /dev/null +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml @@ -0,0 +1,23 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: Role +metadata: + name: user-service-read-secrets + namespace: prod +rules: + - apiGroups: [ "v1" ] + resources: [ "secrets" ] + verbs: [get, list] +--- +apiVersion: rbac.authorization.k8s.io/v1 +kind: RoleBinding +metadata: + name: read-secrets + namespace: prod +subjects: + - apiGroup: rbac.authorization.k8s.io + kind: ServiceAccount + name: user-service +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: Role + name: user-service-read-secrets \ No newline at end of file From 7dd76b0d5d2d6233a3837058dc0cea70c28b387a Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 18:32:53 +0100 Subject: [PATCH 08/21] Hotfix: Kubernetes RBAC hotfix --- .../storage-service-manifests/storage-service-rbac.yaml | 2 +- .../kubernetes/user-service-manifests/user-service-rbac.yaml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml index b4c53b7..c66b707 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml @@ -14,7 +14,7 @@ metadata: name: read-secrets namespace: prod subjects: - - apiGroup: rbac.authorization.k8s.io + - apiGroup: v1 kind: ServiceAccount name: storage-service roleRef: diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml index 24c0047..7a322de 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml @@ -14,7 +14,7 @@ metadata: name: read-secrets namespace: prod subjects: - - apiGroup: rbac.authorization.k8s.io + - apiGroup: v1 kind: ServiceAccount name: user-service roleRef: From bb5d4549748595e52af61648f6a46ba48e791dae Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 5 Jan 2026 18:35:26 +0100 Subject: [PATCH 09/21] Hotfix: Kubernetes RBAC hotfix --- .../storage-service-manifests/storage-service-rbac.yaml | 5 ++--- .../kubernetes/user-service-manifests/user-service-rbac.yaml | 5 ++--- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml index c66b707..6104f33 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml @@ -4,7 +4,7 @@ metadata: name: storage-service-read-secrets namespace: prod rules: - - apiGroups: [ "v1" ] + - apiGroups: [ "" ] resources: [ "secrets" ] verbs: [get, list] --- @@ -14,8 +14,7 @@ metadata: name: read-secrets namespace: prod subjects: - - apiGroup: v1 - kind: ServiceAccount + - kind: ServiceAccount name: storage-service roleRef: apiGroup: rbac.authorization.k8s.io diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml index 7a322de..90f36c9 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml @@ -4,7 +4,7 @@ metadata: name: user-service-read-secrets namespace: prod rules: - - apiGroups: [ "v1" ] + - apiGroups: [ "" ] resources: [ "secrets" ] verbs: [get, list] --- @@ -14,8 +14,7 @@ metadata: name: read-secrets namespace: prod subjects: - - apiGroup: v1 - kind: ServiceAccount + - kind: ServiceAccount name: user-service roleRef: apiGroup: rbac.authorization.k8s.io From 1aa38de19b50758a5ce96727f7d05c082b534b6f Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Tue, 6 Jan 2026 02:07:29 +0100 Subject: [PATCH 10/21] Fix: Fixed repository auth bugs --- .../key-vault-external-secrets.yaml | 5 ++++- infrastructure/prod/terraform/main.tf | 13 +++++++++++-- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index fa5b919..bd3c617 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -56,13 +56,16 @@ spec: .dockerconfigjson: | # Token username is the same as ACR name { "auths": { - "{{ .token }}.azurecr.io": { + "{{ .acrName }}.azurecr.io": { "username": "{{ .token }}", "password": "{{ .password }}" } } } data: + - secretKey: acrName + remoteRef: + key: secret/acr-name - secretKey: token remoteRef: key: secret/aks-acr-token diff --git a/infrastructure/prod/terraform/main.tf b/infrastructure/prod/terraform/main.tf index 8d47b67..0d38ddf 100644 --- a/infrastructure/prod/terraform/main.tf +++ b/infrastructure/prod/terraform/main.tf @@ -457,6 +457,10 @@ module "azure_aks" { tags = var.azure_application_tags } +locals { # Local variable to pass in ACR config and Secret config + aks_acr_token = "aks-token" +} + # Azure Container Registry module "azure_container_registry" { source = "Azure/avm-res-containerregistry-registry/azurerm" @@ -481,7 +485,7 @@ module "azure_container_registry" { description = "Read only all repositories" registry_tokens = { akstoken = { - name = "aks-token" + name = local.aks_acr_token passwords = { password1 = { # Expiration date for token password expiry = "2026-12-31T00:00:00Z" @@ -590,6 +594,10 @@ module "devops_key_vault" { name = "cloudflare-api-token" tags = var.azure_application_tags } + acr_name = { + name = "acr-name" + tags = var.azure_application_tags + } aks_registry_token = { name = "aks-acr-token" tags = var.azure_application_tags @@ -615,7 +623,8 @@ module "devops_key_vault" { cloudflare_r2_api_uri = "https://${cloudflare_r2_custom_domain.devops_r2_custom_domain.domain}/${cloudflare_r2_bucket.devops_r2_bucket.name}" cloudflare_r2_account_id = var.cloudflare_account_id cloudflare_api_token = var.cloudflare_api_token - aks_registry_token = module.azure_container_registry.name + acr_name = module.azure_container_registry.name + aks_registry_token = local.aks_acr_token # Here we need to pass ACR token name aks_registry_password = local.container_registry_aks_password postgresql_uri = data.azurerm_postgresql_flexible_server.devops_postgresql.fqdn postgresql_username = data.azurerm_postgresql_flexible_server.devops_postgresql.administrator_login From 4759ed6f31f7962e100373d151b643ebb60e2cd7 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Tue, 6 Jan 2026 18:14:30 +0100 Subject: [PATCH 11/21] Fix: Fixed Private DNS zones for Azure Container Registry, fixed External Secrets templates for backend microservices --- .../key-vault-external-secrets.yaml | 9 ++-- .../storage-service-deployment-v1.0.yaml | 4 +- .../storage-service-rbac.yaml | 2 +- .../user-service-deployment-v1.0.yaml | 10 ++-- .../user-service-rbac.yaml | 2 +- infrastructure/prod/terraform/main.tf | 50 +++++++++---------- 6 files changed, 38 insertions(+), 39 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index bd3c617..fd83718 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -88,11 +88,10 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: - postgresql: | # Complete URI for JDBC with TLS required - uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require - username: {{ .username }} - password: {{ .password }} + data: # Complete URI for JDBC with TLS required + uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require + username: {{ .username }} + password: {{ .password }} data: - secretKey: uri remoteRef: diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml index 7c14409..e9b2ee2 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml @@ -18,8 +18,6 @@ spec: app: storage-service version: v1.0 spec: - imagePullSecrets: # Setting credentials to Azure Container Registry, synchronized with Key Vault - - name: azurecr-credentials containers: - name: storage-service image: acrdevopsprojectprod.azurecr.io/storage-service:dev @@ -65,5 +63,7 @@ spec: port: 8080 initialDelaySeconds: 15 periodSeconds: 10 + imagePullSecrets: # Setting credentials to Azure Container Registry, synchronized with Key Vault + - name: azurecr-credentials restartPolicy: Always serviceAccountName: storage-service \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml index 6104f33..17ab0a3 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-rbac.yaml @@ -11,7 +11,7 @@ rules: apiVersion: rbac.authorization.k8s.io/v1 kind: RoleBinding metadata: - name: read-secrets + name: storage-service-read-secrets namespace: prod subjects: - kind: ServiceAccount diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml index 8c36ec3..74009ab 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml @@ -18,8 +18,6 @@ spec: app: user-service version: v1.0 spec: - imagePullSecrets: # Setting credentials to Azure Container Registry, synchronized with Key Vault - - name: azurecr-credentials containers: - name: user-service image: acrdevopsprojectprod.azurecr.io/user-service:dev @@ -33,17 +31,17 @@ spec: valueFrom: secretKeyRef: name: postgresql-credentials - key: postgresql.uri + key: uri - name: POSTGRESQL_USERNAME valueFrom: secretKeyRef: name: postgresql-credentials - key: postgresql.username + key: username - name: POSTGRESQL_PASSWORD valueFrom: secretKeyRef: name: postgresql-credentials - key: postgresql.password + key: password ports: - containerPort: 8080 protocol: TCP @@ -65,5 +63,7 @@ spec: port: 8080 initialDelaySeconds: 15 periodSeconds: 10 + imagePullSecrets: # Setting credentials to Azure Container Registry, synchronized with Key Vault + - name: azurecr-credentials restartPolicy: Always serviceAccountName: user-service \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml index 90f36c9..ae53689 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-rbac.yaml @@ -11,7 +11,7 @@ rules: apiVersion: rbac.authorization.k8s.io/v1 kind: RoleBinding metadata: - name: read-secrets + name: user-service-read-secrets namespace: prod subjects: - kind: ServiceAccount diff --git a/infrastructure/prod/terraform/main.tf b/infrastructure/prod/terraform/main.tf index 0d38ddf..3380672 100644 --- a/infrastructure/prod/terraform/main.tf +++ b/infrastructure/prod/terraform/main.tf @@ -517,28 +517,10 @@ data "azurerm_container_registry" "azure_container_registry" { } locals { - keyvault_private_endpoint_ip = data.azurerm_private_endpoint_connection.key_vault_private_endpoint.private_service_connection[0].private_ip_address - containerregistry_private_endpoint_ip = data.azurerm_private_endpoint_connection.container_registry_private_endpoint.private_service_connection[0].private_ip_address - postgresql_private_endpoint_ip = data.azurerm_private_endpoint_connection.postgresql_private_endpoint.private_service_connection[0].private_ip_address - container_registry_aks_password = module.azure_container_registry.scope_maps["aksscope"].registry_token_passwords["akstoken"].password1[0].value -} - -data "azurerm_private_endpoint_connection" "key_vault_private_endpoint" { - name = "KeyVaultPrivateEndpoint" - resource_group_name = module.azure_resource_group.name - depends_on = [module.devops_key_vault] -} - -data "azurerm_private_endpoint_connection" "container_registry_private_endpoint" { - name = "ContainerRegistryPrivateEndpoint" - resource_group_name = module.azure_resource_group.name - depends_on = [module.azure_container_registry] -} - -data "azurerm_private_endpoint_connection" "postgresql_private_endpoint" { - name = "PostgresqlPrivateEndpoint" - resource_group_name = module.azure_resource_group.name - depends_on = [module.devops_postgresql] + keyvault_private_endpoint_ip = data.azurerm_private_endpoint_connection.key_vault_private_endpoint.private_service_connection[0].private_ip_address + postgresql_private_endpoint_ip = data.azurerm_private_endpoint_connection.postgresql_private_endpoint.private_service_connection[0].private_ip_address + container_registry_main_endpoint_ip = data.azurerm_network_interface.container_registry_main_private_endpoint.private_ip_addresses[1] # This is a list, fist address is matching .data subdomain so if we need to retrieve address for main subdomain it must select second address in a list + container_registry_aks_password = module.azure_container_registry.scope_maps["aksscope"].registry_token_passwords["akstoken"].password1[0].value } # Azure Key Vault @@ -675,12 +657,30 @@ module "devops_postgresql" { tags = var.azure_application_tags } +# In this section we need to retrieve IPv4 addresses from Private Endpoint configurations data "azurerm_postgresql_flexible_server" "devops_postgresql" { name = module.devops_postgresql.name resource_group_name = module.azure_resource_group.name depends_on = [module.devops_postgresql] } +data "azurerm_private_endpoint_connection" "key_vault_private_endpoint" { + name = "KeyVaultPrivateEndpoint" + resource_group_name = module.azure_resource_group.name + depends_on = [module.devops_key_vault] +} + +data "azurerm_private_endpoint_connection" "postgresql_private_endpoint" { + name = "PostgresqlPrivateEndpoint" + resource_group_name = module.azure_resource_group.name + depends_on = [module.devops_postgresql] +} + +data "azurerm_network_interface" "container_registry_main_private_endpoint" { + name = "containerregistry-${module.azure_naming.network_interface.name}${local.env}" + resource_group_name = module.azure_resource_group.name +} + # Private DNS Zones (These are very important because we can use TLS protocol in isolated private Azure network without exposing endpoints outside. Azure usually provides TLS wildcard certs that we can use with resource name as subdomain) module "devops_key_vault_private_dns_zone" { source = "Azure/avm-res-network-privatednszone/azurerm" @@ -712,11 +712,11 @@ module "devops_container_registry_private_dns_zone" { version = "0.4.3" domain_name = "azurecr.io" parent_id = module.azure_resource_group.resource_id - a_records = { - acr = { + a_records = { # I don't know why ACR module enter primary (data) Private DNS record automatically, I had some bugs with that because methods used in other resources (DB, Key Vault) are using one IPv4 address and one domain per resource. I couldn't pull images from registry because DNS records weren't configured correctly + acr_io = { name = module.azure_container_registry.name ttl = 5 - ip_addresses = [local.containerregistry_private_endpoint_ip] + ip_addresses = [local.container_registry_main_endpoint_ip] } } virtual_network_links = { From 043d07901398776d63ab2ae079516f3ba78e434f Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Tue, 6 Jan 2026 18:16:48 +0100 Subject: [PATCH 12/21] Hotfix: External Secret for user-service --- .../external-secrets-manifests/key-vault-external-secrets.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index fd83718..810921a 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -88,7 +88,7 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: # Complete URI for JDBC with TLS required + data: | # Complete URI for JDBC with TLS required uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require username: {{ .username }} password: {{ .password }} From 01225ba1829aea156d260b550dce5e90f292d9a0 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Tue, 6 Jan 2026 18:22:30 +0100 Subject: [PATCH 13/21] Hotfix: External Secret for user-service --- .../external-secrets-manifests/key-vault-external-secrets.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index 810921a..fd83718 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -88,7 +88,7 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: | # Complete URI for JDBC with TLS required + data: # Complete URI for JDBC with TLS required uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require username: {{ .username }} password: {{ .password }} From c29498bc52d7fb2417d03a35bab2248172d73cde Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Tue, 6 Jan 2026 19:45:30 +0100 Subject: [PATCH 14/21] Hotfix: External Secret for user-service --- .../key-vault-external-secrets.yaml | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index fd83718..bd3c617 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -88,10 +88,11 @@ spec: name: postgresql-credentials creationPolicy: Owner template: - data: # Complete URI for JDBC with TLS required - uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require - username: {{ .username }} - password: {{ .password }} + data: + postgresql: | # Complete URI for JDBC with TLS required + uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require + username: {{ .username }} + password: {{ .password }} data: - secretKey: uri remoteRef: From 85ab1ede592df4f72dc1454f76af7d0379a3a411 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Tue, 6 Jan 2026 22:36:13 +0100 Subject: [PATCH 15/21] Fix: External Secret for user-service, Istio fix --- .../key-vault-external-secrets.yaml | 12 ++++++------ .../storage-service-virtual-service.yaml | 6 ++++++ .../user-service-virtual-service.yaml | 6 ++++++ 3 files changed, 18 insertions(+), 6 deletions(-) diff --git a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml index bd3c617..ea6ff8f 100644 --- a/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml +++ b/infrastructure/prod/kubernetes/external-secrets-manifests/key-vault-external-secrets.yaml @@ -87,12 +87,12 @@ spec: target: name: postgresql-credentials creationPolicy: Owner - template: - data: - postgresql: | # Complete URI for JDBC with TLS required - uri: jdbc:postgresql://{{ .uri }}/devops?&sslmode=require - username: {{ .username }} - password: {{ .password }} + template: # Here we are using templating engine to create secret ready to be used in Spring application + engineVersion: v2 + data: # Complete URI for JDBC with TLS required + uri: "jdbc:postgresql://{{ .uri }}/devops?&sslmode=require" + username: "{{ .username }}" + password: "{{ .password }}" data: - secretKey: uri remoteRef: diff --git a/infrastructure/prod/kubernetes/istio-manifests/storage-service-virtual-service.yaml b/infrastructure/prod/kubernetes/istio-manifests/storage-service-virtual-service.yaml index 12cc455..e77b174 100644 --- a/infrastructure/prod/kubernetes/istio-manifests/storage-service-virtual-service.yaml +++ b/infrastructure/prod/kubernetes/istio-manifests/storage-service-virtual-service.yaml @@ -15,13 +15,19 @@ spec: route: - destination: host: storage-service.prod.svc.cluster.local + port: + number: 8080 subset: v1 weight: 100 # We declare that all traffic is routed to v1.0 version - destination: host: storage-service.prod.svc.cluster.local + port: + number: 8080 subset: v2 weight: 0 - destination: host: storage-service.prod.svc.cluster.local + port: + number: 8080 subset: v3 weight: 0 \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/istio-manifests/user-service-virtual-service.yaml b/infrastructure/prod/kubernetes/istio-manifests/user-service-virtual-service.yaml index bfab57a..2c6c446 100644 --- a/infrastructure/prod/kubernetes/istio-manifests/user-service-virtual-service.yaml +++ b/infrastructure/prod/kubernetes/istio-manifests/user-service-virtual-service.yaml @@ -15,13 +15,19 @@ spec: route: - destination: host: user-service.prod.svc.cluster.local + port: + number: 8080 subset: v1 weight: 100 # We declare that all traffic is routed to v1.0 version - destination: host: user-service.prod.svc.cluster.local + port: + number: 8080 subset: v2 weight: 0 - destination: host: user-service.prod.svc.cluster.local + port: + number: 8080 subset: v3 weight: 0 \ No newline at end of file From 22748456f40f2899b648b6df1f261c34b82619fd Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Wed, 7 Jan 2026 10:13:27 +0100 Subject: [PATCH 16/21] Update: Configured Istio manifests, Envoy proxy sidecars, Kubernetes NetworkPolicies --- .../argocd-app-of-apps/config-rabbitmq.yaml | 1 - .../rabbitmq-cluster-config.yaml | 5 +++-- .../storage-service-deployment-v1.0.yaml | 2 +- .../storage-service-network-policy-v1.0.yaml | 15 +++++++++------ .../user-service-deployment-v1.0.yaml | 2 +- .../user-service-network-policy-v1.0.yaml | 15 +++++++++------ infrastructure/prod/kubernetes/values.yaml | 2 ++ .../controller/StorageController.java | 12 ++++++++---- .../com/devops/userservice/config/WebConfig.java | 2 +- .../userservice/controller/UserController.java | 12 ++++++++---- 10 files changed, 42 insertions(+), 26 deletions(-) diff --git a/infrastructure/prod/kubernetes/argocd-app-of-apps/config-rabbitmq.yaml b/infrastructure/prod/kubernetes/argocd-app-of-apps/config-rabbitmq.yaml index 7250ae4..672536c 100644 --- a/infrastructure/prod/kubernetes/argocd-app-of-apps/config-rabbitmq.yaml +++ b/infrastructure/prod/kubernetes/argocd-app-of-apps/config-rabbitmq.yaml @@ -25,6 +25,5 @@ spec: app.kubernetes.io/component: rabbitmq-operator app.kubernetes.io/name: rabbitmq-system app.kubernetes.io/part-of: rabbitmq - istio-injection: enabled # To inject sidecar proxy automatically we need set this label syncOptions: - CreateNamespace=true \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml b/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml index d30da2f..934ec97 100644 --- a/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml +++ b/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml @@ -3,14 +3,15 @@ kind: RabbitmqCluster metadata: name: devops-project-cluster namespace: rabbitmq-system - labels: - istio-injection: enabled # To inject sidecar proxy automatically we need to set this label spec: replicas: 1 override: statefulSet: spec: template: + metadata: + labels: + sidecar.istio.io/inject: true # To inject sidecar proxy automatically we need to set this label (Pod level) That way we prevent injecting to deployments where there is no need spec: containers: - name: rabbitmq diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml index e9b2ee2..a6bd2d5 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml @@ -20,7 +20,7 @@ spec: spec: containers: - name: storage-service - image: acrdevopsprojectprod.azurecr.io/storage-service:dev + image: acrdevopsprojectprod.azurecr.io/storage-service:v1.0 imagePullPolicy: IfNotPresent env: - name: SERVER_PORT diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml index 31c750d..d113075 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml @@ -10,11 +10,14 @@ spec: version: v1.0 policyTypes: - Ingress + - Egress ingress: - - from: - - namespaceSelector: - matchLabels: - kubernetes.io/metadata.name: prod - ports: + - ports: - protocol: TCP - port: 8080 \ No newline at end of file + port: 8080 # Service HTTP port + egress: + - ports: + - protocol: TCP + port: 5672 # Default RabbitMQ broker port + - protocol: TCP + port: 5432 # Default Postgresql port \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml index 74009ab..cacdb2d 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml @@ -20,7 +20,7 @@ spec: spec: containers: - name: user-service - image: acrdevopsprojectprod.azurecr.io/user-service:dev + image: acrdevopsprojectprod.azurecr.io/user-service:v1.0 imagePullPolicy: IfNotPresent env: - name: SERVER_PORT diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml index 04308f4..82cd2f9 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml @@ -10,11 +10,14 @@ spec: version: v1.0 policyTypes: - Ingress + - Egress ingress: - - from: - - namespaceSelector: - matchLabels: - kubernetes.io/metadata.name: prod - ports: + - ports: - protocol: TCP - port: 8080 \ No newline at end of file + port: 8080 # Service port + egress: + - ports: + - protocol: TCP + port: 5672 # Default RabbitMQ broker port + - protocol: TCP + port: 5432 # Default Postgresql port \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/values.yaml b/infrastructure/prod/kubernetes/values.yaml index b8f2b33..79016de 100644 --- a/infrastructure/prod/kubernetes/values.yaml +++ b/infrastructure/prod/kubernetes/values.yaml @@ -4,6 +4,8 @@ configs: cm: statusbadge.enabled: true # -- Enable Status Badge server: # We need to apply additional config to ArgoCD helm chart to proxy traffic via Istio gateway + podLabels: + sidecar.istio.io/inject: true # We are injecting Istio Envoy Proxy Sidecar here using annotation for pods. Only for ArgoCD Server because is used with Ingress Gateway for now extraArgs: - --staticassets - /shared/app diff --git a/storage-service/src/main/java/com/devops/storageservice/controller/StorageController.java b/storage-service/src/main/java/com/devops/storageservice/controller/StorageController.java index b5eb62f..62d7ef5 100644 --- a/storage-service/src/main/java/com/devops/storageservice/controller/StorageController.java +++ b/storage-service/src/main/java/com/devops/storageservice/controller/StorageController.java @@ -5,10 +5,7 @@ import lombok.RequiredArgsConstructor; import com.devops.storageservice.service.StorageService; import org.springframework.http.ResponseEntity; -import org.springframework.web.bind.annotation.PostMapping; -import org.springframework.web.bind.annotation.RequestBody; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RestController; +import org.springframework.web.bind.annotation.*; import java.net.URISyntaxException; @@ -19,6 +16,13 @@ public class StorageController { private final StorageService storageService; + @GetMapping + public ResponseEntity helloStorage() { + return ResponseEntity + .ok() + .body("Hello from storage-service v1 :)"); + } + @PostMapping("/file") ResponseEntity fileUploadRequest(@RequestBody FileUploadRequestDto fileUploadRequestDto) throws URISyntaxException { FileUploadResponseDto fileUploadResponseDto = storageService.fileUploadRequest(fileUploadRequestDto); diff --git a/user-service/src/main/java/com/devops/userservice/config/WebConfig.java b/user-service/src/main/java/com/devops/userservice/config/WebConfig.java index 50a4879..efb090a 100644 --- a/user-service/src/main/java/com/devops/userservice/config/WebConfig.java +++ b/user-service/src/main/java/com/devops/userservice/config/WebConfig.java @@ -12,7 +12,7 @@ public class WebConfig implements WebMvcConfigurer { @Override public void addCorsMappings(CorsRegistry registry) { registry.addMapping("/**") - .allowedOrigins("http://localhost:8500") + .allowedOrigins("http://localhost:8500", "https://devops.kacperklimas.com") .allowedMethods("GET", "POST") .allowedHeaders("*") .allowCredentials(true); diff --git a/user-service/src/main/java/com/devops/userservice/controller/UserController.java b/user-service/src/main/java/com/devops/userservice/controller/UserController.java index 23ac0d9..324d77d 100644 --- a/user-service/src/main/java/com/devops/userservice/controller/UserController.java +++ b/user-service/src/main/java/com/devops/userservice/controller/UserController.java @@ -4,10 +4,7 @@ import com.devops.sharedresources.dto.UserDto; import com.devops.userservice.service.UserService; import org.springframework.http.ResponseEntity; -import org.springframework.web.bind.annotation.PostMapping; -import org.springframework.web.bind.annotation.RequestBody; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RestController; +import org.springframework.web.bind.annotation.*; @RestController @RequestMapping("/api/user") @@ -16,6 +13,13 @@ public class UserController { private final UserService userService; + @GetMapping + public ResponseEntity helloUser() { + return ResponseEntity + .ok() + .body("Hello from user-service v1 :)"); + } + @PostMapping public ResponseEntity createUser(@RequestBody UserDto userDto) { userService.createUser(userDto.getUsername(), userDto.getEmail()); From 6ccc70cd31ac00f3fd5a8269dd8d7a32458dac6a Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Thu, 15 Jan 2026 11:37:06 +0100 Subject: [PATCH 17/21] Fix: Istio injection label fix --- README.md | 0 .../rabbitmq-cluster-config.yaml | 4 +-- .../storage-service-network-policy-v1.0.yaml | 4 +-- .../user-service-network-policy-v1.0.yaml | 2 +- infrastructure/prod/kubernetes/values.yaml | 4 +-- infrastructure/prod/terraform/main.tf | 29 ++++++++++--------- 6 files changed, 21 insertions(+), 22 deletions(-) create mode 100644 README.md diff --git a/README.md b/README.md new file mode 100644 index 0000000..e69de29 diff --git a/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml b/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml index 934ec97..14b8572 100644 --- a/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml +++ b/infrastructure/prod/kubernetes/rabbitmq-manifests/rabbitmq-cluster-config.yaml @@ -10,8 +10,8 @@ spec: spec: template: metadata: - labels: - sidecar.istio.io/inject: true # To inject sidecar proxy automatically we need to set this label (Pod level) That way we prevent injecting to deployments where there is no need + labels: # To inject sidecar proxy automatically we need to set this label (Pod level) That way we prevent injecting to deployments where there is no need + sidecar.istio.io/inject: "true" # Same problem as with ArgoCD but I found solution :) spec: containers: - name: rabbitmq diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml index d113075..fc654ab 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml @@ -18,6 +18,4 @@ spec: egress: - ports: - protocol: TCP - port: 5672 # Default RabbitMQ broker port - - protocol: TCP - port: 5432 # Default Postgresql port \ No newline at end of file + port: 5672 # Default RabbitMQ broker port \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml index 82cd2f9..3570bab 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml @@ -14,7 +14,7 @@ spec: ingress: - ports: - protocol: TCP - port: 8080 # Service port + port: 8080 # Service HTTP port egress: - ports: - protocol: TCP diff --git a/infrastructure/prod/kubernetes/values.yaml b/infrastructure/prod/kubernetes/values.yaml index 79016de..91310c0 100644 --- a/infrastructure/prod/kubernetes/values.yaml +++ b/infrastructure/prod/kubernetes/values.yaml @@ -4,8 +4,8 @@ configs: cm: statusbadge.enabled: true # -- Enable Status Badge server: # We need to apply additional config to ArgoCD helm chart to proxy traffic via Istio gateway - podLabels: - sidecar.istio.io/inject: true # We are injecting Istio Envoy Proxy Sidecar here using annotation for pods. Only for ArgoCD Server because is used with Ingress Gateway for now + podLabels: # We are injecting Istio Envoy Proxy Sidecar here using annotation for pods. Only for ArgoCD Server because is used with Ingress Gateway for now + sidecar.istio.io/inject: "true" # If you don't want a problem with installation remember: If you need to pass some bool value as string use quotation marks "" :) extraArgs: - --staticassets - /shared/app diff --git a/infrastructure/prod/terraform/main.tf b/infrastructure/prod/terraform/main.tf index 3380672..7e2781a 100644 --- a/infrastructure/prod/terraform/main.tf +++ b/infrastructure/prod/terraform/main.tf @@ -679,6 +679,7 @@ data "azurerm_private_endpoint_connection" "postgresql_private_endpoint" { data "azurerm_network_interface" "container_registry_main_private_endpoint" { name = "containerregistry-${module.azure_naming.network_interface.name}${local.env}" resource_group_name = module.azure_resource_group.name + depends_on = [module.azure_container_registry] } # Private DNS Zones (These are very important because we can use TLS protocol in isolated private Azure network without exposing endpoints outside. Azure usually provides TLS wildcard certs that we can use with resource name as subdomain) @@ -712,13 +713,13 @@ module "devops_container_registry_private_dns_zone" { version = "0.4.3" domain_name = "azurecr.io" parent_id = module.azure_resource_group.resource_id - a_records = { # I don't know why ACR module enter primary (data) Private DNS record automatically, I had some bugs with that because methods used in other resources (DB, Key Vault) are using one IPv4 address and one domain per resource. I couldn't pull images from registry because DNS records weren't configured correctly - acr_io = { - name = module.azure_container_registry.name - ttl = 5 - ip_addresses = [local.container_registry_main_endpoint_ip] - } - } + # a_records = { # I don't know why ACR module enter primary (data) Private DNS record automatically, I had some bugs with that because methods used in other resources (DB, Key Vault) are using one IPv4 address and one domain per resource. I couldn't pull images from registry because DNS records weren't configured correctly + # acr_io = { + # name = module.azure_container_registry.name + # ttl = 5 + # ip_addresses = [local.container_registry_main_endpoint_ip] + # } + # } virtual_network_links = { aks = { vnetlinkname = "aksvnetlink" @@ -737,13 +738,13 @@ module "devops_postgresql_private_dns_zone" { version = "0.4.3" domain_name = "postgres.database.azure.com" parent_id = module.azure_resource_group.resource_id - a_records = { - db = { - name = module.devops_postgresql.name - ttl = 5 - ip_addresses = [local.postgresql_private_endpoint_ip] - } - } + # a_records = { # Same problem as with ACR + # db = { + # name = module.devops_postgresql.name + # ttl = 5 + # ip_addresses = [local.postgresql_private_endpoint_ip] + # } + # } virtual_network_links = { aks = { vnetlinkname = "aksvnetlink" From 0835dd0b5cf80c73e12a859e3c5061ae36be1ef3 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Thu, 15 Jan 2026 12:54:59 +0100 Subject: [PATCH 18/21] Test: Using Istio without Kubernetes native NetworkPolicies --- .../storage-service-network-policy-v1.0.yaml | 21 ----------------- .../user-service-network-policy-v1.0.yaml | 23 ------------------- infrastructure/prod/terraform/main.tf | 2 +- 3 files changed, 1 insertion(+), 45 deletions(-) delete mode 100644 infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml delete mode 100644 infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml deleted file mode 100644 index fc654ab..0000000 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-network-policy-v1.0.yaml +++ /dev/null @@ -1,21 +0,0 @@ -apiVersion: networking.k8s.io/v1 -kind: NetworkPolicy -metadata: - name: storage-service-v1.0 - namespace: prod -spec: - podSelector: - matchLabels: - app: storage-service - version: v1.0 - policyTypes: - - Ingress - - Egress - ingress: - - ports: - - protocol: TCP - port: 8080 # Service HTTP port - egress: - - ports: - - protocol: TCP - port: 5672 # Default RabbitMQ broker port \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml deleted file mode 100644 index 3570bab..0000000 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-network-policy-v1.0.yaml +++ /dev/null @@ -1,23 +0,0 @@ -apiVersion: networking.k8s.io/v1 -kind: NetworkPolicy -metadata: - name: user-service-v1.0 - namespace: prod -spec: - podSelector: - matchLabels: - app: user-service - version: v1.0 - policyTypes: - - Ingress - - Egress - ingress: - - ports: - - protocol: TCP - port: 8080 # Service HTTP port - egress: - - ports: - - protocol: TCP - port: 5672 # Default RabbitMQ broker port - - protocol: TCP - port: 5432 # Default Postgresql port \ No newline at end of file diff --git a/infrastructure/prod/terraform/main.tf b/infrastructure/prod/terraform/main.tf index 7e2781a..ffbc416 100644 --- a/infrastructure/prod/terraform/main.tf +++ b/infrastructure/prod/terraform/main.tf @@ -482,7 +482,7 @@ module "azure_container_registry" { aksscope = { name = "aks-scope" # Authorization read only (Pulling images, reading statuses etc) actions = ["repositories/*/content/read", "repositories/*/metadata/read"] - description = "Read only all repositories" + description = "Read-only all repositories" registry_tokens = { akstoken = { name = local.aks_acr_token From 0058c5b4badf9912989f322defa2e10501869b56 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Thu, 15 Jan 2026 13:39:42 +0100 Subject: [PATCH 19/21] Fix: RabbitMQ Istio VirtualService fix --- infrastructure/dev/docker-compose.yaml | 4 ++-- .../rabbitmq-virtual-service.yaml | 20 ++++++++++++++++--- .../storage-service-deployment-v1.0.yaml | 2 +- .../user-service-deployment-v1.0.yaml | 2 +- 4 files changed, 21 insertions(+), 7 deletions(-) diff --git a/infrastructure/dev/docker-compose.yaml b/infrastructure/dev/docker-compose.yaml index a9a53ae..96bcc06 100644 --- a/infrastructure/dev/docker-compose.yaml +++ b/infrastructure/dev/docker-compose.yaml @@ -28,7 +28,7 @@ services: # MICROSERVICES storage-service: - image: storage-service:dev + image: storage-service:v1.0 build: context: ../../storage-service dockerfile: Dockerfile @@ -51,7 +51,7 @@ services: start_interval: 5s user-service: - image: user-service:dev + image: user-service:v1.0 build: context: ../../user-service dockerfile: Dockerfile diff --git a/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml b/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml index 0721ddd..dae2f09 100644 --- a/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml +++ b/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml @@ -25,12 +25,26 @@ metadata: namespace: rabbitmq-system spec: hosts: - - devops-project-cluster.rabbitmq-system.svc.cluster.local + - rabbitmq.rabbitmq-system.svc.cluster.local tcp: - match: - - port: 5672 + - port: 5672 # TCP AMQP route: - destination: host: devops-project-cluster.rabbitmq-system.svc.cluster.local port: - number: 5672 \ No newline at end of file + number: 5672 + - match: + - port: 4369 # TCP EPMD + route: + - destination: + host: devops-project-cluster-nodes.rabbitmq-system.svc.cluster.local + port: + number: 4369 + - match: + - port: 15692 # TCP Prometheus port + route: + - destination: + host: devops-project-cluster.rabbitmq-system.svc.cluster.local + port: + number: 15692 \ No newline at end of file diff --git a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml index a6bd2d5..04e7d22 100644 --- a/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/storage-service-manifests/storage-service-deployment-v1.0.yaml @@ -26,7 +26,7 @@ spec: - name: SERVER_PORT value: "8080" - name: RABBITMQ_HOST - value: devops-project-cluster.rabbitmq-system.svc.cluster.local + value: rabbitmq.rabbitmq-system.svc.cluster.local - name: BUCKET_ENDPOINT valueFrom: secretKeyRef: diff --git a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml index cacdb2d..11c6eb6 100644 --- a/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml +++ b/infrastructure/prod/kubernetes/user-service-manifests/user-service-deployment-v1.0.yaml @@ -26,7 +26,7 @@ spec: - name: SERVER_PORT value: "8080" - name: RABBITMQ_HOST - value: devops-project-cluster.rabbitmq-system.svc.cluster.local + value: rabbitmq.rabbitmq-system.svc.cluster.local - name: POSTGRESQL_URI valueFrom: secretKeyRef: From 342b651cab8f5bb3680ed3f0c62776e4c85002a8 Mon Sep 17 00:00:00 2001 From: Kacper Klimas <135636303+KacperKlimas10@users.noreply.github.com> Date: Mon, 19 Jan 2026 09:14:58 +0100 Subject: [PATCH 20/21] Add image to README for Azure cloud infrastructure --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index e69de29..6e2f653 100644 --- a/README.md +++ b/README.md @@ -0,0 +1 @@ +![Figure 2.1.1 Azure cloud infrastructure deployed automatically via Terraform](https://github.com/user-attachments/assets/1c17cd6d-572b-4426-9d60-d5d1800c0c2d) From 8668bf05c33dd9d1ca68abec59b938de5b68fd36 Mon Sep 17 00:00:00 2001 From: KacperKlimas10 <10kacper.klimas.lo1@gmail.com> Date: Mon, 19 Jan 2026 09:16:08 +0100 Subject: [PATCH 21/21] Fix: RabbitMQ Istio VirtualService fix --- infrastructure/dev/docker-compose.yaml | 37 ++++--------------- .../argocd-app-of-apps/helm-istio-base.yaml | 2 +- .../argocd-app-of-apps/helm-istio-d.yaml | 2 +- .../helm-istio-egress-controller.yaml | 2 +- .../helm-istio-ingress-controller.yaml | 2 +- .../rabbitmq-virtual-service.yaml | 9 +---- infrastructure/prod/terraform/main.tf | 4 +- pom.xml | 4 -- .../storageservice/config/SecurityConfig.java | 25 ++++++++++++- .../storageservice/config/WebConfig.java | 20 ---------- .../userservice/config/SecurityConfig.java | 23 +++++++++++- .../devops/userservice/config/WebConfig.java | 20 ---------- 12 files changed, 60 insertions(+), 90 deletions(-) delete mode 100644 storage-service/src/main/java/com/devops/storageservice/config/WebConfig.java delete mode 100644 user-service/src/main/java/com/devops/userservice/config/WebConfig.java diff --git a/infrastructure/dev/docker-compose.yaml b/infrastructure/dev/docker-compose.yaml index 96bcc06..df9c523 100644 --- a/infrastructure/dev/docker-compose.yaml +++ b/infrastructure/dev/docker-compose.yaml @@ -1,34 +1,9 @@ services: - # API GATEWAY - - kong-cp: - image: '${GW_IMAGE:-kong/kong-gateway:3.11.0.2}' - restart: on-failure - environment: - KONG_DATABASE: off - KONG_DECLARATIVE_CONFIG: /kong/declarative/kong.yaml - KONG_ADMIN_LISTEN: 0.0.0.0:8001, 0.0.0.0:8444 ssl - KONG_ADMIN_GUI_LISTEN: 0.0.0.0:8002, 0.0.0.0:8445 ssl - KONG_ADMIN_GUI_URL: http://${GW_HOST:-localhost}:8002 - KONG_PASSWORD: handyshake - ports: - - "8000:8000" # Proxy HTTP - - "8443:8443" # Proxy HTTPS - - "8001:8001" # Admin API HTTP - - "8444:8444" # Admin API HTTPS - - "8002:8002" # Kong Manager HTTP - - "8445:8445" # Kong Manager HTTPS - networks: - - backend-network - volumes: - - ./kong/kong.yaml:/kong/declarative/kong.yaml - command: kong start - # MICROSERVICES storage-service: - image: storage-service:v1.0 + image: acrdevopsprojectprod.azurecr.io/storage-service:v1.0 build: context: ../../storage-service dockerfile: Dockerfile @@ -38,6 +13,8 @@ services: RABBITMQ_HOST: rabbitmq BUCKET_ENDPOINT: http://minio:9000 AWS_BUCKET_NAME : devops + ports: + - "8080:8080" networks: - backend-network - db-network @@ -51,7 +28,7 @@ services: start_interval: 5s user-service: - image: user-service:v1.0 + image: acrdevopsprojectprod.azurecr.io/user-service:v1.0 build: context: ../../user-service dockerfile: Dockerfile @@ -60,6 +37,8 @@ services: SERVER_PORT: 8080 RABBITMQ_HOST: rabbitmq POSTGRESQL_URI: jdbc:postgresql://postgresql/devops + ports: + - "8081:8080" networks: - backend-network - db-network @@ -151,7 +130,7 @@ services: PGADMIN_DEFAULT_EMAIL: kacper@kacper.pl PGADMIN_DEFAULT_PASSWORD: kacper ports: - - "8080:80" + - "8880:80" networks: - db-network volumes: @@ -161,7 +140,7 @@ services: image: mongo-express:latest restart: on-failure ports: - - "8081:8081" + - "8881:8081" environment: ME_CONFIG_MONGODB_ADMINUSERNAME: kacper ME_CONFIG_MONGODB_ADMINPASSWORD: kacper diff --git a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-base.yaml b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-base.yaml index 2dd69fb..1a01777 100644 --- a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-base.yaml +++ b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-base.yaml @@ -10,7 +10,7 @@ spec: source: chart: base repoURL: https://istio-release.storage.googleapis.com/charts - targetRevision: 1.28.1 + targetRevision: 1.28.2 helm: releaseName: istio-base parameters: diff --git a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-d.yaml b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-d.yaml index 033e714..4bbfb47 100644 --- a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-d.yaml +++ b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-d.yaml @@ -10,7 +10,7 @@ spec: source: chart: istiod repoURL: https://istio-release.storage.googleapis.com/charts - targetRevision: 1.28.1 + targetRevision: 1.28.2 helm: releaseName: istiod destination: diff --git a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-egress-controller.yaml b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-egress-controller.yaml index 863745d..010d07d 100644 --- a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-egress-controller.yaml +++ b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-egress-controller.yaml @@ -12,7 +12,7 @@ spec: source: chart: gateway repoURL: https://istio-release.storage.googleapis.com/charts - targetRevision: 1.28.1 + targetRevision: 1.28.2 helm: releaseName: istio-egressgateway values: | diff --git a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-ingress-controller.yaml b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-ingress-controller.yaml index 32b53f1..629cb32 100644 --- a/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-ingress-controller.yaml +++ b/infrastructure/prod/kubernetes/argocd-app-of-apps/helm-istio-ingress-controller.yaml @@ -12,7 +12,7 @@ spec: source: chart: gateway repoURL: https://istio-release.storage.googleapis.com/charts - targetRevision: 1.28.1 + targetRevision: 1.28.2 helm: releaseName: istio-ingressgateway values: | diff --git a/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml b/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml index dae2f09..16bff9e 100644 --- a/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml +++ b/infrastructure/prod/kubernetes/istio-manifests/rabbitmq-virtual-service.yaml @@ -25,7 +25,7 @@ metadata: namespace: rabbitmq-system spec: hosts: - - rabbitmq.rabbitmq-system.svc.cluster.local + - devops-project-cluster.rabbitmq-system.svc.cluster.local tcp: - match: - port: 5672 # TCP AMQP @@ -34,13 +34,6 @@ spec: host: devops-project-cluster.rabbitmq-system.svc.cluster.local port: number: 5672 - - match: - - port: 4369 # TCP EPMD - route: - - destination: - host: devops-project-cluster-nodes.rabbitmq-system.svc.cluster.local - port: - number: 4369 - match: - port: 15692 # TCP Prometheus port route: diff --git a/infrastructure/prod/terraform/main.tf b/infrastructure/prod/terraform/main.tf index ffbc416..b8fa9a6 100644 --- a/infrastructure/prod/terraform/main.tf +++ b/infrastructure/prod/terraform/main.tf @@ -155,7 +155,7 @@ resource "azurerm_virtual_network_gateway" "vpn_gateway" { resource_group_name = module.azure_resource_group.name type = "Vpn" generation = "Generation1" - sku = "VpnGw2AZ" + sku = "VpnGw2AZ" # Zone-redundant gateway ip_configuration { public_ip_address_id = azurerm_public_ip.vpn_public_ip.id subnet_id = module.azure_management_vnet.subnets["vpnsubnet"].resource_id @@ -165,7 +165,7 @@ resource "azurerm_virtual_network_gateway" "vpn_gateway" { vpn_client_protocols = ["IkeV2", "OpenVPN"] address_space = ["172.16.0.0/24"] root_certificate { - name = "devopsCA" + name = "devopsCA" # Azure documentation says if we want to use self generated certificate we need to take part without --BEGIN CERTIFICATE-- and --END CERTIFICATE-- lines, so we use regular expressions to do that. public_cert_data = replace(file(var.azure_vpn_path_to_cert), "/-.*-/", "") } } diff --git a/pom.xml b/pom.xml index 4bcff74..f7a4336 100644 --- a/pom.xml +++ b/pom.xml @@ -36,10 +36,6 @@ org.springframework.boot spring-boot-starter - - org.springframework - spring-webmvc - org.springframework.boot spring-boot-starter-web diff --git a/storage-service/src/main/java/com/devops/storageservice/config/SecurityConfig.java b/storage-service/src/main/java/com/devops/storageservice/config/SecurityConfig.java index 41ce17a..8bd4068 100644 --- a/storage-service/src/main/java/com/devops/storageservice/config/SecurityConfig.java +++ b/storage-service/src/main/java/com/devops/storageservice/config/SecurityConfig.java @@ -2,10 +2,16 @@ import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; +import org.springframework.security.config.Customizer; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.http.SessionCreationPolicy; import org.springframework.security.web.SecurityFilterChain; +import org.springframework.web.cors.CorsConfiguration; +import org.springframework.web.cors.CorsConfigurationSource; +import org.springframework.web.cors.UrlBasedCorsConfigurationSource; + +import java.util.List; @Configuration @EnableWebSecurity @@ -17,11 +23,26 @@ public SecurityFilterChain filterChain(HttpSecurity http) throws Exception { .sessionManagement((sessionManagement) -> sessionManagement .sessionCreationPolicy(SessionCreationPolicy.STATELESS) ) + .cors(Customizer.withDefaults()) .authorizeHttpRequests((requests) -> requests - .requestMatchers("/**") + .requestMatchers("/actuator/**", "/api/**") .permitAll() .anyRequest().authenticated() ).csrf((csrf) -> csrf.disable()) .build(); } -} + + @Bean + public CorsConfigurationSource corsConfigurationSource() { + CorsConfiguration config = new CorsConfiguration(); + config.setAllowedOriginPatterns(List.of("http://localhost:*", "https://devops.kacperklimas.com")); + config.setAllowedMethods(List.of("GET", "POST", "PUT", "DELETE", "OPTIONS")); + config.setAllowedHeaders(List.of("*")); + config.setAllowCredentials(true); + config.setMaxAge(3600L); + + UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(); + source.registerCorsConfiguration("/**", config); + return source; + } +} \ No newline at end of file diff --git a/storage-service/src/main/java/com/devops/storageservice/config/WebConfig.java b/storage-service/src/main/java/com/devops/storageservice/config/WebConfig.java deleted file mode 100644 index e0a38d0..0000000 --- a/storage-service/src/main/java/com/devops/storageservice/config/WebConfig.java +++ /dev/null @@ -1,20 +0,0 @@ -package com.devops.storageservice.config; - -import org.springframework.stereotype.Component; -import org.springframework.web.servlet.config.annotation.CorsRegistry; -import org.springframework.web.servlet.config.annotation.EnableWebMvc; -import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; - -@Component -@EnableWebMvc -public class WebConfig implements WebMvcConfigurer { - - @Override - public void addCorsMappings(CorsRegistry registry) { - registry.addMapping("/**") - .allowedOrigins("http://localhost:8501") - .allowedMethods("GET", "POST") - .allowedHeaders("*") - .allowCredentials(true); - } -} diff --git a/user-service/src/main/java/com/devops/userservice/config/SecurityConfig.java b/user-service/src/main/java/com/devops/userservice/config/SecurityConfig.java index 5987d21..8a47020 100644 --- a/user-service/src/main/java/com/devops/userservice/config/SecurityConfig.java +++ b/user-service/src/main/java/com/devops/userservice/config/SecurityConfig.java @@ -2,10 +2,16 @@ import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; +import org.springframework.security.config.Customizer; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.http.SessionCreationPolicy; import org.springframework.security.web.SecurityFilterChain; +import org.springframework.web.cors.CorsConfiguration; +import org.springframework.web.cors.CorsConfigurationSource; +import org.springframework.web.cors.UrlBasedCorsConfigurationSource; + +import java.util.List; @Configuration @EnableWebSecurity @@ -17,11 +23,26 @@ public SecurityFilterChain filterChain(HttpSecurity http) throws Exception { .sessionManagement((sessionManagement) -> sessionManagement .sessionCreationPolicy(SessionCreationPolicy.STATELESS) ) + .cors(Customizer.withDefaults()) .authorizeHttpRequests((requests) -> requests - .requestMatchers("/**") + .requestMatchers("/actuator/**", "/api/**") .permitAll() .anyRequest().authenticated() ).csrf((csrf) -> csrf.disable()) .build(); } + + @Bean + public CorsConfigurationSource corsConfigurationSource() { + CorsConfiguration config = new CorsConfiguration(); + config.setAllowedOriginPatterns(List.of("http://localhost:*", "https://devops.kacperklimas.com")); + config.setAllowedMethods(List.of("GET", "POST", "PUT", "DELETE", "OPTIONS")); + config.setAllowedHeaders(List.of("*")); + config.setAllowCredentials(true); + config.setMaxAge(3600L); + + UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(); + source.registerCorsConfiguration("/**", config); + return source; + } } diff --git a/user-service/src/main/java/com/devops/userservice/config/WebConfig.java b/user-service/src/main/java/com/devops/userservice/config/WebConfig.java deleted file mode 100644 index efb090a..0000000 --- a/user-service/src/main/java/com/devops/userservice/config/WebConfig.java +++ /dev/null @@ -1,20 +0,0 @@ -package com.devops.userservice.config; - -import org.springframework.stereotype.Component; -import org.springframework.web.servlet.config.annotation.CorsRegistry; -import org.springframework.web.servlet.config.annotation.EnableWebMvc; -import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; - -@Component -@EnableWebMvc -public class WebConfig implements WebMvcConfigurer { - - @Override - public void addCorsMappings(CorsRegistry registry) { - registry.addMapping("/**") - .allowedOrigins("http://localhost:8500", "https://devops.kacperklimas.com") - .allowedMethods("GET", "POST") - .allowedHeaders("*") - .allowCredentials(true); - } -}