feat: add Grafana, Loki, and Alloy services to Docker configurations for Dev, Prod, and QA environments

This commit is contained in:
Juan Felipe Zapata Moreno 2026-03-31 14:06:17 -06:00
parent d10b578c61
commit ea2dd1b3ff
12 changed files with 373 additions and 5 deletions

25
Docker/Dev/config.alloy Normal file
View File

@ -0,0 +1,25 @@
logging {
level = "info"
format = "logfmt"
}
// Descubrir archivos de log
local.file_match "laravel_logs" {
path_targets = [
{ __path__ = "/var/log/repuve/padron-estatal.log", job = "padron_estatal", env = "dev" },
{ __path__ = "/var/log/repuve/repuve-nacional.log", job = "repuve_nacional", env = "dev" },
]
}
// Leer los archivos
loki.source.file "laravel_reader" {
targets = local.file_match.laravel_logs.targets
forward_to = [loki.write.local.receiver]
}
// Enviar a Loki
loki.write "local" {
endpoint {
url = "http://loki:3100/loki/api/v1/push"
}
}

View File

@ -56,7 +56,7 @@ services:
MYSQL_PASSWORD: ${DB_PASSWORD} MYSQL_PASSWORD: ${DB_PASSWORD}
MYSQL_USER: ${DB_USERNAME} MYSQL_USER: ${DB_USERNAME}
ports: ports:
- "${DB_PORT}:3306" - "${DB_PORT_FORWARD}:3306"
volumes: volumes:
- mysql_data:/var/lib/mysql - mysql_data:/var/lib/mysql
networks: networks:
@ -68,9 +68,60 @@ services:
timeout: 15s timeout: 15s
retries: 10 retries: 10
alloy:
image: grafana/alloy:latest
command:
- run
- /etc/alloy/config.alloy
- --server.http.listen-addr=0.0.0.0:12345
ports:
- "12345:12345"
volumes:
- ./config.alloy:/etc/alloy/config.alloy
- ../../storage/logs:/var/log/repuve:ro
networks:
- repuve-dev-network
restart: unless-stopped
depends_on:
- repuve-backend
- loki
loki:
image: grafana/loki:latest
user: "0"
ports:
- "3100:3100"
volumes:
- ./loki-config.yml:/etc/loki/local-config.yaml
- loki_data:/loki
command: -config.file=/etc/loki/local-config.yaml
networks:
- repuve-dev-network
restart: unless-stopped
grafana:
image: grafana/grafana:latest
ports:
- "8702:3000"
environment:
- GF_AUTH_ANONYMOUS_ENABLED=true
- GF_AUTH_ANONYMOUS_ORG_ROLE=Viewer
volumes:
- grafana_data:/var/lib/grafana
- ./grafana/provisioning:/etc/grafana/provisioning
networks:
- repuve-dev-network
restart: unless-stopped
depends_on:
- loki
volumes: volumes:
mysql_data: mysql_data:
driver: local driver: local
loki_data:
driver: local
grafana_data:
driver: local
networks: networks:
repuve-dev-network: repuve-dev-network:

View File

@ -0,0 +1,39 @@
auth_enabled: false
server:
http_listen_port: 3100
ingester:
lifecycler:
address: 127.0.0.1
ring:
kvstore:
store: inmemory
replication_factor: 1
final_sleep: 0s
chunk_idle_period: 5m
chunk_retain_period: 30s
schema_config:
configs:
- from: 2020-10-24
store: tsdb
object_store: filesystem
schema: v13
index:
prefix: index_
period: 24h
storage_config:
tsdb_shipper:
active_index_directory: /loki/tsdb-active
cache_location: /loki/tsdb-cache
filesystem:
directory: /loki/chunks
limits_config:
reject_old_samples: true
reject_old_samples_max_age: 168h
compactor:
working_directory: /loki/compactor

25
Docker/Prod/config.alloy Normal file
View File

@ -0,0 +1,25 @@
logging {
level = "warn"
format = "logfmt"
}
// Descubrir archivos de log de Laravel
local.file_match "laravel_logs" {
path_targets = [
{ __path__ = "/var/log/repuve/padron-estatal.log", job = "padron_estatal", env = "prod" },
{ __path__ = "/var/log/repuve/repuve-nacional.log", job = "repuve_nacional", env = "prod" },
]
}
// Leer los archivos
loki.source.file "laravel_reader" {
targets = local.file_match.laravel_logs.targets
forward_to = [loki.write.local.receiver]
}
// Enviar a Loki
loki.write "local" {
endpoint {
url = "http://loki:3100/loki/api/v1/push"
}
}

View File

@ -68,9 +68,57 @@ services:
timeout: 15s timeout: 15s
retries: 10 retries: 10
alloy:
image: grafana/alloy:latest
command:
- run
- /etc/alloy/config.alloy
- --server.http.listen-addr=0.0.0.0:12345
ports:
- "127.0.0.1:12345:12345"
volumes:
- ./config.alloy:/etc/alloy/config.alloy
- ../../storage/logs:/var/log/repuve:ro
networks:
- repuve-prod-network
restart: unless-stopped
depends_on:
- repuve-backend
- loki
loki:
image: grafana/loki:latest
user: "0"
ports:
- "127.0.0.1:3100:3100"
volumes:
- ./loki-config.yml:/etc/loki/local-config.yaml
- loki_data:/loki
command: -config.file=/etc/loki/local-config.yaml
networks:
- repuve-prod-network
restart: unless-stopped
grafana:
image: grafana/grafana:latest
ports:
- "127.0.0.1:8700:3000"
volumes:
- grafana_data:/var/lib/grafana
- ./grafana/provisioning:/etc/grafana/provisioning
networks:
- repuve-prod-network
restart: unless-stopped
depends_on:
- loki
volumes: volumes:
mysql_data: mysql_data:
driver: local driver: local
loki_data:
driver: local
grafana_data:
driver: local
networks: networks:
repuve-prod-network: repuve-prod-network:

View File

@ -0,0 +1,10 @@
apiVersion: 1
datasources:
- name: Loki
type: loki
access: proxy
url: http://loki:3100
isDefault: true
jsonData:
maxLines: 1000

View File

@ -0,0 +1,39 @@
auth_enabled: false
server:
http_listen_port: 3100
ingester:
lifecycler:
address: 127.0.0.1
ring:
kvstore:
store: inmemory
replication_factor: 1
final_sleep: 0s
chunk_idle_period: 5m
chunk_retain_period: 30s
schema_config:
configs:
- from: 2020-10-24
store: tsdb
object_store: filesystem
schema: v13
index:
prefix: index_
period: 24h
storage_config:
tsdb_shipper:
active_index_directory: /loki/tsdb-active
cache_location: /loki/tsdb-cache
filesystem:
directory: /loki/chunks
limits_config:
reject_old_samples: true
reject_old_samples_max_age: 168h
compactor:
working_directory: /loki/compactor

25
Docker/QA/config.alloy Normal file
View File

@ -0,0 +1,25 @@
logging {
level = "info"
format = "logfmt"
}
// Descubrir archivos de log de Laravel
local.file_match "laravel_logs" {
path_targets = [
{ __path__ = "/var/log/repuve/padron-estatal.log", job = "padron_estatal", env = "qa" },
{ __path__ = "/var/log/repuve/repuve-nacional.log", job = "repuve_nacional", env = "qa" },
]
}
// Leer los archivos
loki.source.file "laravel_reader" {
targets = local.file_match.laravel_logs.targets
forward_to = [loki.write.local.receiver]
}
// Enviar a Loki
loki.write "local" {
endpoint {
url = "http://loki:3100/loki/api/v1/push"
}
}

View File

@ -70,9 +70,60 @@ services:
mem_limit: 256M mem_limit: 256M
restart: unless-stopped restart: unless-stopped
alloy:
image: grafana/alloy:latest
command:
- run
- /etc/alloy/config.alloy
- --server.http.listen-addr=0.0.0.0:12345
ports:
- "12346:12345"
volumes:
- ./config.alloy:/etc/alloy/config.alloy
- ../../storage/logs:/var/log/repuve:ro
networks:
- repuve-qa-network
restart: unless-stopped
depends_on:
- repuve-backend
- loki
loki:
image: grafana/loki:latest
user: "0"
ports:
- "3200:3100"
volumes:
- ./loki-config.yml:/etc/loki/local-config.yaml
- qa_loki_data:/loki
command: -config.file=/etc/loki/local-config.yaml
networks:
- repuve-qa-network
restart: unless-stopped
grafana:
image: grafana/grafana:latest
ports:
- "8701:3000"
environment:
- GF_AUTH_ANONYMOUS_ENABLED=true
- GF_AUTH_ANONYMOUS_ORG_ROLE=Viewer
volumes:
- qa_grafana_data:/var/lib/grafana
- ./grafana/provisioning:/etc/grafana/provisioning
networks:
- repuve-qa-network
restart: unless-stopped
depends_on:
- loki
networks: networks:
repuve-qa-network: repuve-qa-network:
driver: bridge driver: bridge
volumes: volumes:
qa_mysql_data: qa_mysql_data:
qa_loki_data:
driver: local
qa_grafana_data:
driver: local

View File

@ -0,0 +1,10 @@
apiVersion: 1
datasources:
- name: Loki
type: loki
access: proxy
url: http://loki:3100
isDefault: true
jsonData:
maxLines: 1000

39
Docker/QA/loki-config.yml Normal file
View File

@ -0,0 +1,39 @@
auth_enabled: false
server:
http_listen_port: 3100
ingester:
lifecycler:
address: 127.0.0.1
ring:
kvstore:
store: inmemory
replication_factor: 1
final_sleep: 0s
chunk_idle_period: 5m
chunk_retain_period: 30s
schema_config:
configs:
- from: 2020-10-24
store: tsdb
object_store: filesystem
schema: v13
index:
prefix: index_
period: 24h
storage_config:
tsdb_shipper:
active_index_directory: /loki/tsdb-active
cache_location: /loki/tsdb-cache
filesystem:
directory: /loki/chunks
limits_config:
reject_old_samples: true
reject_old_samples_max_age: 168h
compactor:
working_directory: /loki/compactor

View File

@ -124,16 +124,22 @@
"composer run broadcast:status" "composer run broadcast:status"
], ],
"docker:dev:up": [ "docker:dev:up": [
"docker compose -f Docker/Dev/docker-compose.yml --env-file .env up -d --build" "docker compose -f Docker/Dev/docker-compose.yml --env-file Docker/Dev/.env up -d --build"
], ],
"docker:dev:down": [ "docker:dev:down": [
"docker compose -f Docker/Dev/docker-compose.yml --env-file .env down" "docker compose -f Docker/Dev/docker-compose.yml --env-file Docker/Dev/.env down --remove-orphans"
], ],
"docker:prod:up": [ "docker:prod:up": [
"docker compose -f Docker/Prod/docker-compose.yml --env-file .env up -d --build" "docker compose -f Docker/Prod/docker-compose.yml --env-file Docker/Prod/.env up -d --build"
], ],
"docker:prod:down": [ "docker:prod:down": [
"docker compose -f Docker/Prod/docker-compose.yml --env-file .env down" "docker compose -f Docker/Prod/docker-compose.yml --env-file Docker/Prod/.env down"
],
"docker:qa:up": [
"docker compose -f Docker/QA/docker-compose.yml --env-file Docker/QA/.env up -d --build"
],
"docker:qa:down": [
"docker compose -f Docker/QA/docker-compose.yml --env-file Docker/QA/.env down"
] ]
}, },
"extra": { "extra": {