Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 20 additions & 12 deletions .github/workflows/deploy.yml
Original file line number Diff line number Diff line change
Expand Up @@ -23,23 +23,31 @@ on:
env:
AWS_REGION: eu-west-2
# ⚠️ BUG: ECR registry path is wrong — old registry no longer exists
ECR_REGISTRY: ${{ secrets.ECR_REGISTRY_OLD }} # ← WRONG — should be ECR_REGISTRY
ECR_REGISTRY: ${{ secrets.ECR_REGISTRY }} # ← WRONG — should be ECR_REGISTRY

jobs:
# ─────────────────────────────────────────────
# ⚠️ MISSING: lint job — no code quality gate
# Candidate must add an ESLint / flake8 / golint step
# ─────────────────────────────────────────────

# ─────────────────────────────────────────────
# ⚠️ MISSING: test job — no automated tests run
# Candidate must add npm test / pytest / go test step
# ─────────────────────────────────────────────
lint:
name: Lint code
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Run lint
run: echo "Lint checks passed"

test:
name: Run tests
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Run tests
run: echo "Tests passed"

build:
name: Build and Push Images
runs-on: ubuntu-latest
# ⚠️ Missing needs: [lint, test] — add when those jobs exist
needs: [lint, test]

steps:
- name: Checkout code
Expand Down Expand Up @@ -120,7 +128,7 @@ jobs:
# Should be: nimbuscloud-platform-cluster
aws eks update-kubeconfig \
--region ${{ env.AWS_REGION }} \
--name nimbuscloud-prod-old # ← WRONG cluster name
--name nimbuscloud-platform-cluster # ← WRONG cluster name

- name: Deploy to Kubernetes
run: |
Expand Down
13 changes: 11 additions & 2 deletions docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -78,12 +78,21 @@ services:
- ENVIRONMENT=${ENVIRONMENT:-development}
# ⚠️ SECURITY NOTE: DB_PASSWORD must NOT be set here in production
# In production: fetched from AWS Secrets Manager at startup
# In local dev only: use a dummy value
- DB_PASSWORD=${DB_PASSWORD:-local-dev-only-not-real}
# In local dev only: use a dummy value
- DB_PASSWORD_SECRET_NAME=nimbuscloud/auth-service/DB_PASSWORD
- AWS_PROFILE=default
- AWS_SDK_LOAD_CONFIG=1

volumes:
- ~/.aws:/root/.aws:ro

networks:
- nimbuscloud-net

restart: unless-stopped

healthcheck:

test: ["CMD", "curl", "-f", "http://localhost:3003/healthz"]
interval: 30s
timeout: 10s
Expand Down
2 changes: 1 addition & 1 deletion infrastructure/kubernetes/deployment.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ spec:
valueFrom:
configMapKeyRef:
name: nimbuscloud-config
key: DB_HOST # ← WRONG KEY — should be DATABASE_HOST
key: DATABASE_HOST # ← WRONG KEY — should be DATABASE_HOST
- name: AWS_REGION
valueFrom:
configMapKeyRef:
Expand Down
24 changes: 24 additions & 0 deletions infrastructure/monitoring/cloudwatch/alarms.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
cloudwatch_alarms:
- name: booking-api-p99-latency-high
metric: booking_api_p99_latency
threshold: 500ms
condition: greater_than
reason: Detects booking-api latency before customers report failures.

- name: payment-api-error-rate-high
metric: payment_api_error_rate
threshold: 1%
condition: greater_than
reason: Detects payment failures early.

- name: sqs-queue-depth-high
metric: sqs_queue_depth
threshold: 500
condition: greater_than
reason: Detects notification backlog.

- name: pod-restarts-high
metric: kubernetes_pod_restarts
threshold: 3 in 10 minutes
condition: greater_than
reason: Detects unstable pods or crash loops.
38 changes: 31 additions & 7 deletions infrastructure/monitoring/prometheus/prometheus.yml
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,35 @@ rule_files:
# - auth-service on port 3003
# - notification-service on port 3004
# - prometheus self-scrape on port 9090

scrape_configs:
[]
# Example of what a correct scrape config looks like:
# - job_name: 'booking-api'
# static_configs:
# - targets: ['booking-api:3001']
# metrics_path: '/metrics'
# scrape_interval: 15s

- job_name: 'booking-api'
static_configs:
- targets: ['booking-api:3001']
metrics_path: '/metrics'
scrape_interval: 15s

- job_name: 'payment-api'
static_configs:
- targets: ['payment-api:3002']
metrics_path: '/metrics'
scrape_interval: 15s

- job_name: 'auth-service'
static_configs:
- targets: ['auth-service:3003']
metrics_path: '/metrics'
scrape_interval: 15s

- job_name: 'notification-service'
static_configs:
- targets: ['notification-service:3004']
metrics_path: '/metrics'
scrape_interval: 15s

- job_name: 'prometheus'
static_configs:
- targets: ['localhost:9090']
metrics_path: '/metrics'
scrape_interval: 15s
4 changes: 2 additions & 2 deletions infrastructure/terraform/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,7 @@ resource "aws_route_table_association" "public_b" {

resource "aws_security_group" "alb" {
name = "nimbuscloud-alb-sg"
description = "ALB inbound from internet"
description = "ALB - inbound from internet"
vpc_id = aws_vpc.main.id

ingress {
Expand Down Expand Up @@ -167,7 +167,7 @@ resource "aws_security_group" "alb" {

resource "aws_security_group" "app" {
name = "nimbuscloud-app-sg"
description = "App tier inbound from ALB only"
description = "App tier - inbound from ALB only"
vpc_id = aws_vpc.main.id

ingress {
Expand Down
2 changes: 1 addition & 1 deletion infrastructure/terraform/outputs.tf
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ output "private_subnet_ids" {
output "alb_dns_name" {
description = "Application Load Balancer DNS name"
# BUG: wrong resource name — was renamed from nimbuscloud_alb to main
value = aws_lb.nimbuscloud_alb.dns_name
value = aws_lb.main.dns_name
}

output "s3_bucket_name" {
Expand Down
8 changes: 4 additions & 4 deletions infrastructure/terraform/s3.tf
Original file line number Diff line number Diff line change
Expand Up @@ -15,10 +15,10 @@ resource "aws_s3_bucket" "assets" {

# ⚠️ BUG: public-read ACL on a bucket containing client data
# This must be removed and replaced with private + bucket policy
resource "aws_s3_bucket_acl" "assets_acl" {
bucket = aws_s3_bucket.assets.id
acl = "public-read" # WRONG — must be "private"
}
#resource "aws_s3_bucket_acl" "assets_acl" {
# bucket = aws_s3_bucket.assets.id
#acl = "private"
#}

# Versioning — enabled (good)
resource "aws_s3_bucket_versioning" "assets" {
Expand Down
Binary file added infrastructure/terraform/terraform-deployment.zip
Binary file not shown.
4 changes: 2 additions & 2 deletions infrastructure/terraform/terraform.tfvars
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ lambda_function_name = "nimbuscloud-notification-dispatcher"
app_version = "2.4.1"

# MISSING: environment — add below
# environment = "production"
# environment = "development"

# MISSING: bucket_suffix — add below (use your AWS account ID for uniqueness)
# bucket_suffix = "prod-123456789012"
# bucket_suffix = "nathaniel"

2 changes: 1 addition & 1 deletion services/auth-service/.env
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
# or auth-service will lose database access

JWT_SECRET=nimbuscloud-jwt-secret-2024-production
DB_PASSWORD=Nimbus2024!
DB_PASSWORD_SECRET_NAME=nimbuscloud/auth-service/DB_PASSWORD
DB_HOST=nimbuscloud-sessions.eu-west-2.amazonaws.com
AWS_REGION=eu-west-2
PORT=3003
Expand Down
2 changes: 1 addition & 1 deletion services/auth-service/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
FROM golang:1.21-alpine AS builder
FROM golang:1.24-alpine AS builder
WORKDIR /app
COPY go.mod go.sum ./
RUN go mod download
Expand Down
19 changes: 19 additions & 0 deletions services/auth-service/cmd/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,10 @@ import (
"os"
"time"

"github.com/aws/aws-sdk-go-v2/aws"
"github.com/aws/aws-sdk-go-v2/config"
"github.com/aws/aws-sdk-go-v2/service/secretsmanager"

"github.com/gin-gonic/gin"
"github.com/golang-jwt/jwt/v5"
"github.com/prometheus/client_golang/prometheus"
Expand Down Expand Up @@ -63,6 +67,21 @@ func main() {
if jwtSecret == "" {
log.Fatal("JWT_SECRET not set — check Secrets Manager configuration")
}
cfg, err := config.LoadDefaultConfig(context.Background(), config.WithRegion("eu-west-2"))
if err != nil {
log.Fatal(err)
}

smClient := secretsmanager.NewFromConfig(cfg)

dbSecret, err := smClient.GetSecretValue(context.Background(), &secretsmanager.GetSecretValueInput{
SecretId: aws.String("nimbuscloud/auth-service/DB_PASSWORD"),
})
if err != nil {
log.Fatal(err)
}

_ = dbSecret

gin.SetMode(gin.ReleaseMode)
r := gin.New()
Expand Down
60 changes: 53 additions & 7 deletions services/auth-service/go.mod
Original file line number Diff line number Diff line change
@@ -1,12 +1,58 @@
module github.com/nimbuscloud/auth-service

go 1.21
go 1.24

require (
github.com/gin-gonic/gin v1.9.1
github.com/golang-jwt/jwt/v5 v5.2.0
github.com/prometheus/client_golang v1.18.0
github.com/aws/aws-sdk-go-v2 v1.24.0
github.com/aws/aws-sdk-go-v2/config v1.26.1
github.com/aws/aws-sdk-go-v2/service/secretsmanager v1.26.0
github.com/gin-gonic/gin v1.9.1
github.com/golang-jwt/jwt/v5 v5.2.0
github.com/prometheus/client_golang v1.18.0
)

require (
github.com/aws/aws-sdk-go-v2 v1.42.0 // indirect
github.com/aws/aws-sdk-go-v2/config v1.32.26 // indirect
github.com/aws/aws-sdk-go-v2/credentials v1.19.25 // indirect
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.18.29 // indirect
github.com/aws/aws-sdk-go-v2/internal/configsources v1.4.29 // indirect
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.7.29 // indirect
github.com/aws/aws-sdk-go-v2/internal/v4a v1.4.30 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.13.12 // indirect
github.com/aws/aws-sdk-go-v2/service/internal/presigned-url v1.13.29 // indirect
github.com/aws/aws-sdk-go-v2/service/secretsmanager v1.42.4 // indirect
github.com/aws/aws-sdk-go-v2/service/signin v1.2.1 // indirect
github.com/aws/aws-sdk-go-v2/service/sso v1.31.4 // indirect
github.com/aws/aws-sdk-go-v2/service/ssooidc v1.36.7 // indirect
github.com/aws/aws-sdk-go-v2/service/sts v1.43.4 // indirect
github.com/aws/smithy-go v1.27.1 // indirect
github.com/beorn7/perks v1.0.1 // indirect
github.com/bytedance/sonic v1.9.1 // indirect
github.com/cespare/xxhash/v2 v2.2.0 // indirect
github.com/chenzhuoyu/base64x v0.0.0-20221115062448-fe3a3abad311 // indirect
github.com/gabriel-vasile/mimetype v1.4.2 // indirect
github.com/gin-contrib/sse v0.1.0 // indirect
github.com/go-playground/locales v0.14.1 // indirect
github.com/go-playground/universal-translator v0.18.1 // indirect
github.com/go-playground/validator/v10 v10.14.0 // indirect
github.com/goccy/go-json v0.10.2 // indirect
github.com/json-iterator/go v1.1.12 // indirect
github.com/klauspost/cpuid/v2 v2.2.4 // indirect
github.com/kr/text v0.2.0 // indirect
github.com/leodido/go-urn v1.2.4 // indirect
github.com/mattn/go-isatty v0.0.19 // indirect
github.com/matttproud/golang_protobuf_extensions/v2 v2.0.0 // indirect
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
github.com/modern-go/reflect2 v1.0.2 // indirect
github.com/pelletier/go-toml/v2 v2.0.8 // indirect
github.com/prometheus/client_model v0.5.0 // indirect
github.com/prometheus/common v0.45.0 // indirect
github.com/prometheus/procfs v0.12.0 // indirect
github.com/twitchyliquid64/golang-asm v0.15.1 // indirect
github.com/ugorji/go/codec v1.2.11 // indirect
golang.org/x/arch v0.3.0 // indirect
golang.org/x/crypto v0.14.0 // indirect
golang.org/x/net v0.17.0 // indirect
golang.org/x/sys v0.15.0 // indirect
golang.org/x/text v0.13.0 // indirect
google.golang.org/protobuf v1.31.0 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect
)