התעמקות באובייקט האופן תכלת Collector

הקולקטור של OpenTelemetry נמצא במרכז ארכיטקטורת OpenTelemetry אך אינו קשור ל-W3C Trace Context. בהדגמת המעקב שלי הדגמת מעקב, אני משתמש ב-Jaeger במקום בקולקטור. עם זאת, הוא נפוץ, כפי שנמצא בכל פוסט שקשור ל-OpenTelemetry. רציתי לחקור אותו עוד.

בפוסט זה, אני חוקר את היבטים שונים של הקולקטור:

  • סוג הנתונים: יומנים, מדדים ועקבות
  • מודלים דחיפה ומשיכה
  • פעולות: קריאות, שינויים וכתיבה

צעדים ראשונים

A long time ago, observability as we know it didn't exist; what we had instead was monitoring. Back then, monitoring was a bunch of people looking at screens displaying dashboards. Dashboards themselves consisted of metrics and only system metrics, mainly CPU, memory, and disk usage. For this reason, we will start with metrics.

Prometheus הוא אחד מהפתרונות העיקריים למעקב אחר תיקיות. הוא פועל במודל משיכה: Prometheus מקלט נקודות מקבילות של היישומים שלך ומאחסן אותם בפנים.

נשתמש בקולקטור OTEL כדי לגלות נקודת מקבילות מתאימה ל-Prometheus ולהדפיס את התוצאה בתצוגה מקדימה. Grafana Labs מציעה פרויקט המייצר מדדים אקראיים לשיחק איתם. לשם פשטות, אשתמש ב-Docker Compose; הסטודה נראית כך:

YAML

 

version: "3"

services:
  fake-metrics:
    build: ./fake-metrics-generator                                         #1
  collector:
    image: otel/opentelemetry-collector:0.87.0                              #2
    environment:                                                            #3
      - METRICS_HOST=fake-metrics
      - METRICS_PORT=5000
    volumes:
      - ./config/collector/config.yml:/etc/otelcol/config.yaml:ro           #4

  1. אין תמונת Docker זמינה עבור פרויקט המדדים המalsoף; לכן, עלינו לבנות אותו
  2. גרסה האחרונה של הקולקטור OTEL בזמן כתיבת הפוסט
  3. לממש את הקובץ התיאורטי הבא
  4. הכל קורה כאן

כפי שציינתי לעיל, הקולקטור OTEL יכול לעשות הרבה. לכן, ההתאמה היא הכול.

YAML

 

receivers:                                                                  #1
  prometheus:                                                               #2
    config:
      scrape_configs:                                                       #3
        - job_name: fake-metrics                                            #4
          scrape_interval: 3s
          static_configs:
            - targets: [ "${env.METRICS_HOST}:${env.METRICS_PORT}" ]
            
exporters:                                                                  #5
  logging:                                                                  #6
    loglevel: debug
    
service:
  pipelines:                                                                #7
    metrics:                                                                #8
      receivers: [ "prometheus" ]                                           #9
      exporters: [ "logging" ]                                              #10

  1. רשימת מקבלים. מקבל קורא נתונים; הוא יכול להיות מבוסס דחיפה או מבוסס משיכה.
  2. אנו משתמשים במקבל מוגדר מראש של prometheus
  3. הגדרת משימות משיכה
  4. הגדרת ה組態 של המשימה
  5. רשימת מייצגים. בניגוד למקבלים, מייצג כותב נתונים.
  6. המייצג הפשוט ביותר הוא לכתוב נתונים בפלט התקני
  7. צינורות מרכיבים מקבלים ומייצגים
  8. הגדרת צינורת מדדים
  9. הצינור מקבל נתונים מהמקבל prometheus המוגדר קודם ושולח אותם למייצג logging, כלומר, מדפיס אותם

הנה דוגמה לתוצאה:

2023-11-11 08:28:54 otel-collector-collector-1     | StartTimestamp: 1970-01-01 00:00:00 +0000 UTC
2023-11-11 08:28:54 otel-collector-collector-1     | Timestamp: 2023-11-11 07:28:54.14 +0000 UTC
2023-11-11 08:28:54 otel-collector-collector-1     | Value: 83.090000
2023-11-11 08:28:54 otel-collector-collector-1     | NumberDataPoints #1
2023-11-11 08:28:54 otel-collector-collector-1     | Data point attributes:
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__embrace_world_class_systems: Str(concept)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__exploit_magnetic_applications: Str(concept)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__facilitate_wireless_architectures: Str(extranet)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__grow_magnetic_communities: Str(challenge)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__reinvent_revolutionary_applications: Str(support)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__strategize_strategic_initiatives: Str(internet_solution)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__target_customized_eyeballs: Str(concept)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__transform_turn_key_technologies: Str(framework)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__whiteboard_innovative_partnerships: Str(matrices)
2023-11-11 08:28:54 otel-collector-collector-1     | StartTimestamp: 1970-01-01 00:00:00 +0000 UTC
2023-11-11 08:28:54 otel-collector-collector-1     | Timestamp: 2023-11-11 07:28:54.14 +0000 UTC
2023-11-11 08:28:54 otel-collector-collector-1     | Value: 53.090000
2023-11-11 08:28:54 otel-collector-collector-1     | NumberDataPoints #2
2023-11-11 08:28:54 otel-collector-collector-1     | Data point attributes:
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__expedite_distributed_partnerships: Str(approach)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__facilitate_wireless_architectures: Str(graphical_user_interface)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__grow_magnetic_communities: Str(policy)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__reinvent_revolutionary_applications: Str(algorithm)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__transform_turn_key_technologies: Str(framework)
2023-11-11 08:28:54 otel-collector-collector-1     | StartTimestamp: 1970-01-01 00:00:00 +0000 UTC
2023-11-11 08:28:54 otel-collector-collector-1     | Timestamp: 2023-11-11 07:28:54.14 +0000 UTC
2023-11-11 08:28:54 otel-collector-collector-1     | Value: 16.440000
2023-11-11 08:28:54 otel-collector-collector-1     | NumberDataPoints #3
2023-11-11 08:28:54 otel-collector-collector-1     | Data point attributes:
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__exploit_magnetic_applications: Str(concept)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__grow_magnetic_communities: Str(graphical_user_interface)
2023-11-11 08:28:54 otel-collector-collector-1     |      -> fake__target_customized_eyeballs: Str(extranet)

מעבר להדפסה

הנהלון לעיל הוא צעד ראשון מצוין, אך יש יותר מדי הדפסה לתוך קונסולת. אנו נחשף את המדדים לגרום להם להתחתן על ידי מצב תקין של Prometheus; נוכל להוסיף לוח תצוגה של Grafana כדי להמחיש אותם. ואף על פי שזה עשוי להיראות חסר תועלת, תמשיכו איתו, שכן זהו רק מדרגה.

כדי להשיג את הנקודה לעיל, אנו משנים רק את הגדרת OTEL Collector:

YAML

 

exporters:
  prometheus:                                                               #1
    endpoint: ":${env:PROMETHEUS_PORT}"                                     #2

service:
  pipelines:
    metrics:
      receivers: [ "prometheus" ]
      exporters: [ "prometheus" ]                                           #3

  1. הוספת מייצג prometheus
  2. חשוף נקודת קצה מקבילה ל-Prometheus
  3. החלפת הדפסה בחשיפה

זהו זה. OTEL Collector הוא מאוד גמיש.

שים לב שהמוסד מקבל מספר קלטים, פלט מספר. כדי להדפיס נתונים ולחשוף אותם דרך הנקודת הקצה, אנו מוסיפים אותם לצינור:

YAML

 

exporters:
  prometheus:                                                               #1
    endpoint: ":${env:PROMETHEUS_PORT}"
  logging:                                                                  #2
    loglevel: debug

service:
  pipelines:
    metrics:
      receivers: [ "prometheus" ]
      exporters: [ "prometheus", "logging" ]                                #3

  1. חשוף נתונים
  2. הדפסת נתונים
  3. הזרמים ידפיסו גם נתונים ויחשפו אותם

עם מגבר ה-Prometheus מוגדר, אנו יכולים להמחיש מדדים ב-Grafana.

שים לב שמקבלים ומגברים מציינים את סוגם והם כל אחד מהם חייב להיות ייחודי. כדי לעמוד בדרישה האחרונה, נוכל להוסיף מושג מפריד כדי להבחין ביניהם, כלומר, prometheus/foo ו-prometheus/bar.

עיבוד נתונים ביניים

A valid question would be why the OTEL Collector is set between the source and Prometheus, as it makes the overall design more fragile. At this stage, we can leverage the true power of the OTEL Collector: data processing. So far, we have ingested raw metrics, but the source format may not be adapted to how we want to visualize data. For example, in our setup, metrics come from our fake generator, "business," and the underlying NodeJS platform, "technical." It is reflected in the metrics' name. We could add a dedicated source label and remove the unnecessary prefix to filter more efficiently.

אתה מצהיר על מעבדי נתונים בסעיף processors של קובץ ה конפיגורציה. האיסוף מבצע אותם בסדר שבו הם מצוינים. בואו ניישם את השינוי הנ"ל.

הצעד הראשון לקראת המטרה שלנו הוא להבין שיש שתי גרסאות של האיסוף: גרסה "ריקה" וגרסה contrib שבונה על גביה. המעבדים המוכלים באחת הם מוגבלים, הן במספר והן ביכולות; לכן, אנו צריכים לעבור לגרסה contrib.

YAML

 

collector:
  image: otel/opentelemetry-collector-contrib:0.87.0                        #1
  environment:
    - METRICS_HOST=fake-metrics
    - METRICS_PORT=5000
    - PROMETHEUS_PORT=8889
  volumes:
    - ./config/collector/config.yml:/etc/otelcol-contrib/config.yaml:ro     #2

  1. השתמש בטעם contrib
  2. למשתוללים, קובץ ההגדרה נמצא בנתיב אחר

בשלב זה, אנו יכולים להוסיף את המעבד עצמו:

YAML

 

processors:
  metricstransform:                                                         #1
    transforms:                                                             #2
      - include: ^fake_(.*)$                                                #3
        match_type: regexp                                                  #3
        action: update
        operations:                                                         #4
          - action: add_label                                               #5
            new_label: origin
            new_value: fake
      - include: ^fake_(.*)$
        match_type: regexp
        action: update                                                      #6
        new_name: $${1}                                                     #6-7
# עשה את אותו הדבר עם מדדים שנוצרו על ידי NodeJS

  1. הזמנת מעבד השינוי של המדדים
  2. רשימת השינויים המופעלים בסדר
  3. מתאים לכל המדדים עם הרגיסטר המוגדר
  4. רשימת הפעולות המופעלות בסדר
  5. הוסף את התיוג
  6. שנה את המדד על ידי הסרת קידומת קבוצת הרגיסטר
  7. דברים מהנים: התחביר הוא $${x}

לבסוף, אנו מוסיפים את המעבד המוגדר לזרם:

YAML

 

service:
  pipelines:
    metrics:
      receivers: [ "prometheus" ]
      processors: [ "metricstransform" ]
      exporters: [ "prometheus" ]

הנה התוצאות:

חיבור מקלטים וייצוא

A connector is both a receiver and an exporter and connects two pipelines. The example from the documentation receives the number of spans (tracing) and exports the count, which has a metric. I tried to achieve the same with 500 errors — spoiler: it doesn't work as intended.

בואו קודם כל נוסיף מקלט יומן:

YAML

 

receivers:
  filelog:
    include: [ "/var/logs/generated.log" ]

לאחר מכן, נוסיף חיבור:

YAML

 

connectors:
  count:
    requests.errors:
      description: Number of 500 errors
      condition: [ "status == 500 " ]

לבסוף, נחבר את מקלט היומן וייצוא המדדים:

YAML

 

service:
   pipelines:
     logs:
       receivers: [ "filelog" ]
       exporters: [ "count" ]
     metrics:
       receivers: [ "prometheus", "count" ]

המדד נקרא log_record_count_total, אך ערכו נשאר ב-1.

שינוי יומני ה로ג

מעבדים מאפשרים שינוי נתונים; מפעילים הם מעבדים מיוחדים העובדים על יומני ה로ג. אם אתה מכיר את ערוץ ELK הערוץ, הם המקביל של Logstash.

כרגע, תאריך היישום של היומן הוא תאריך היישום. נשנה אותו לתאריך יצירתו.

YAML

 

receivers:
  filelog:
    include: [ "/var/logs/generated.log" ]
    operators:
      - type: json_parser                                                   #1
        timestamp:                                                          #2
          parse_from: attributes.datetime                                   #3
          layout: "%d/%b/%Y:%H:%M:%S %z"                                    #4
        severity:                                                           #2
          parse_from: attributes.status                                     #3
          mapping:                                                          #5
            error: 5xx                                                      #6
            warn: 4xx
            info: 3xx
            debug: 2xx
      - id: remove_body                                                     #7
        type: remove
        field: body
      - id: remove_datetime                                                 #7
        type: remove
        field: attributes.datetime
      - id: remove_status                                                   #7
        type: remove
        field: attributes.status

  1. היומן בפורמט JSON; נוכל להשתמש במסנן JSON המוצע
  2. תכונות מטא-נתונים להגדיר
  3. שדות לקרוא ממנו
  4. תבנית פילוט
  5. טבלת מיפוי
  6. לקבל טווח, לדוגמה, 501-599. למפעיל ערך מובא מיוחד 5xx (וכדומה) עבור סטטוס HTTP.
  7. להסרת נתונים מקבילים

יומני ה-

בנקודה זו, אנו יכולים לשלוח את יומני ה- לכל רכיב איחוד יומנים. אנו נשארים בתוך המסע ה- Grafana Labs ונשתמש ב-Loki.

YAML

 

exporters:
  loki:
    endpoint: "http://loki:3100/loki/api/v1/push"

אנו יכולים גם להשתמש ביומנים מהקולקטור עצמו:

YAML

 

service:
  telemetry:
    logs:

לבסוף, בואו נוסיף עוד זרם:

YAML

 

service:
  pipelines:
    logs:
      receivers: [ "filelog" ]
      exporters: [ "loki" ]

Grafana יכולה גם להמחיש את היומנים. בחר Loki כמקור נתונים.

מסקנה

בפוסט הזה, חקרנו את קולקטור OpenTelemetry. בעוד שזה לא חלק חובה מארכיטקטורת OTEL, זו סכין שוויצרית שימושית לכל צרכי העיבוד הנתונים שלך. במידה ואתה לא תקוע במסד נתונים ספציפי או שאינך רוצה, זה עזרה עצומה.

קוד המקור המלא לפוסט זה ניתן למצוא בGitHub.

להמשיך רחוק יותר

Source:
https://dzone.com/articles/exploring-the-opentelemetry-collector