configmap-vector.yaml 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. apiVersion: v1
  2. kind: ConfigMap
  3. metadata:
  4. name: vector-config
  5. namespace: {{ .Release.Namespace }}
  6. labels:
  7. app: vector
  8. data:
  9. vector.toml: |
  10. # Vector config adapted from Log.md
  11. [sources.kubernetes_logs]
  12. type = "kubernetes_logs"
  13. include_namespaces = ["{{ .Values.vector.namespace }}"]
  14. # read pod/container logs under /var/log/pods
  15. host_path = "/var/log"
  16. [transforms.parse_json]
  17. type = "remap"
  18. inputs = ["kubernetes_logs"]
  19. source = '''
  20. parsed = parse_json!(.message)
  21. .ts = parsed.ts
  22. .level = parsed.level
  23. .app = parsed.app
  24. .env = parsed.env
  25. .traceId = parsed.traceId
  26. .uri = parsed.uri
  27. .uri_group = parsed.uri_group
  28. .duration_ms = to_int!(parsed.duration, 0)
  29. .userId = parsed.userId
  30. .event = parsed.event
  31. .error = parsed.error
  32. .status = parsed.status
  33. .event_class = parsed.event_class
  34. # fallback derive event_class from uri_group
  35. if starts_with(.uri_group, "/order") {
  36. .event_class = "order"
  37. } else if starts_with(.uri_group, "/payment") {
  38. .event_class = "payment"
  39. } else if !exists(.event_class) {
  40. .event_class = "api"
  41. }
  42. # keep kubernetes metadata as labels fields
  43. .k8s_ns = .kubernetes.namespace_name
  44. .k8s_pod = .kubernetes.pod_name
  45. .k8s_labels = .kubernetes.labels
  46. '''
  47. [transforms.filter_services]
  48. type = "filter"
  49. inputs = ["parse_json"]
  50. # keep only selected apps (based on k8s labels.app or parsed .app)
  51. condition = '(.kubernetes.labels.app in {{ toJson .Values.vector.logSelector }}) || (.app in {{ toJson .Values.vector.logSelector }})'
  52. [transforms.filter_levels]
  53. type = "filter"
  54. inputs = ["filter_services"]
  55. condition = '.level != "DEBUG" && .level != "TRACE"'
  56. [sinks.loki]
  57. type = "loki"
  58. inputs = ["filter_levels"]
  59. endpoint = "{{ .Values.vector.loki.endpoint }}"
  60. encoding.codec = "json"
  61. [sinks.loki.labels]
  62. env = "{{ env }}"
  63. app = "{{ app }}"
  64. level = "{{ level }}"
  65. event_class = "{{ event_class }}"
  66. uri_group = "{{ uri_group }}"
  67. status = "{{ status }}"
  68. [transforms.to_metrics]
  69. type = "log_to_metric"
  70. inputs = ["filter_levels"]
  71. # Counter: Total requests per app/uri_group/status
  72. [[transforms.to_metrics.metrics]]
  73. type = "counter"
  74. field = "message"
  75. name = "requests_total"
  76. tags.app = "{{ app }}"
  77. tags.env = "{{ env }}"
  78. tags.uri_group = "{{ uri_group }}"
  79. # Counter: HTTP request errors
  80. [[transforms.to_metrics.metrics]]
  81. type = "counter"
  82. field = "message"
  83. name = "requests_errors_total"
  84. filter.condition = '.status == "server_error" || .status == "client_error"'
  85. tags.app = "{{ app }}"
  86. tags.env = "{{ env }}"
  87. tags.status = "{{ status }}"
  88. # Histogram: Request duration (latency)
  89. [[transforms.to_metrics.metrics]]
  90. type = "histogram"
  91. field = "duration_ms"
  92. name = "request_duration_ms"
  93. tags.app = "{{ app }}"
  94. tags.uri_group = "{{ uri_group }}"
  95. tags.env = "{{ env }}"
  96. # Counter: Total orders
  97. [[transforms.to_metrics.metrics]]
  98. type = "counter"
  99. field = "message"
  100. name = "orders_total"
  101. filter.condition = '.event_class == "order"'
  102. tags.app = "{{ app }}"
  103. tags.env = "{{ env }}"
  104. # Counter: Failed orders
  105. [[transforms.to_metrics.metrics]]
  106. type = "counter"
  107. field = "message"
  108. name = "orders_failed_total"
  109. filter.condition = '.event_class == "order" && (.status == "server_error" || .status == "client_error")'
  110. tags.app = "{{ app }}"
  111. tags.env = "{{ env }}"
  112. # Counter: Payment events
  113. [[transforms.to_metrics.metrics]]
  114. type = "counter"
  115. field = "message"
  116. name = "payment_events_total"
  117. filter.condition = '.event_class == "payment"'
  118. tags.app = "{{ app }}"
  119. tags.env = "{{ env }}"
  120. [sinks.prometheus]
  121. type = "prometheus_exporter"
  122. inputs = ["to_metrics"]
  123. address = "{{ .Values.vector.prometheus.exporterAddress }}"
  124. default_namespace = "shop_recycle"