diff --git a/README.md b/README.md index d508630a..38346e28 100644 --- a/README.md +++ b/README.md @@ -168,6 +168,10 @@ It seems that right now, you have to make a manual step on Azure to use this new Docker container and update it on Azure. Please ask Lorenz for more information. +#### Prod Monitoring on New Relic + +See docs/new-relic.md + ### CapRover vbv-develop Bitbucket Pipelines name: develop diff --git a/docs/new-relic.md b/docs/new-relic.md new file mode 100644 index 00000000..5e3d575c --- /dev/null +++ b/docs/new-relic.md @@ -0,0 +1,15 @@ +# New Relic + +Die Applikation via Docker direkt in NewRelic als APM "vbv-prod-azure" eingebunden: +https://one.newrelic.com/nr1-core/apm/overview/MTgwMTYwfEFQTXxBUFBMSUNBVElPTnwxMDQ5Njk0MDU0 + +Ausserdem können die Applikations-Logs direkt im NewRelic eingesehen werden, innerhalb der APM Applikation +https://one.newrelic.com/nr1-core/logger/logs-summary/MTgwMTYwfEFQTXxBUFBMSUNBVElPTnwxMDQ5Njk0MDU0 + +Hier eine Query wie man nur die relevanten Logs mit einem "event"-Attribute und ohne label==security anzeigen kann: + +``` +event:* -"label":"security" +``` + +![new_relic_logs01.png](new_relic_logs01.png) diff --git a/docs/new_relic_logs01.png b/docs/new_relic_logs01.png new file mode 100644 index 00000000..20d0520c Binary files /dev/null and b/docs/new_relic_logs01.png differ diff --git a/server/config/settings/base.py b/server/config/settings/base.py index abc0cb7a..87ffd78f 100644 --- a/server/config/settings/base.py +++ b/server/config/settings/base.py @@ -8,7 +8,7 @@ import structlog from environs import Env from vbv_lernwelt.core.constants import DEFAULT_RICH_TEXT_FEATURES -from vbv_lernwelt.core.utils import ( +from vbv_lernwelt.core.log_utils import ( structlog_add_app_info, structlog_convert_to_json_for_new_relic, ) diff --git a/server/vbv_lernwelt/core/log_utils.py b/server/vbv_lernwelt/core/log_utils.py new file mode 100644 index 00000000..118ab60b --- /dev/null +++ b/server/vbv_lernwelt/core/log_utils.py @@ -0,0 +1,26 @@ +import logging + +from django.conf import settings +from structlog.typing import EventDict + +from vbv_lernwelt.core.utils import safe_json_dumps + + +def structlog_convert_to_json_for_new_relic( + _: logging.Logger, __: str, event_dict: EventDict +) -> str: + """ + The *event_dict* is serialized to a json string, so that in New Relic logs + the nested keys will show up as attributes. + """ + return safe_json_dumps(event_dict) + + +def structlog_add_app_info( + _: logging.Logger, __: str, event_dict: EventDict +) -> EventDict: + event_dict["django_app"] = "vbv_lernwelt" + event_dict["app_environment"] = settings.APP_ENVIRONMENT + event_dict["django_app_dev_mode"] = f"vbv_lernwelt_{settings.APP_ENVIRONMENT}" + + return event_dict diff --git a/server/vbv_lernwelt/core/utils.py b/server/vbv_lernwelt/core/utils.py index f40ff491..1f4e16fc 100644 --- a/server/vbv_lernwelt/core/utils.py +++ b/server/vbv_lernwelt/core/utils.py @@ -1,21 +1,7 @@ import json -import logging import re -import structlog -from django.conf import settings from rest_framework.throttling import UserRateThrottle -from structlog.types import EventDict - - -def structlog_add_app_info( - _: logging.Logger, __: str, event_dict: EventDict -) -> EventDict: - event_dict["django_app"] = "vbv_lernwelt" - event_dict["app_environment"] = settings.APP_ENVIRONMENT - event_dict["django_app_dev_mode"] = f"vbv_lernwelt_{settings.APP_ENVIRONMENT}" - - return event_dict class FailSafeJSONEncoder(json.JSONEncoder): @@ -30,30 +16,6 @@ def safe_json_dumps(data, **kwargs): return json.dumps(data, cls=FailSafeJSONEncoder, **kwargs) -def structlog_convert_to_json_for_new_relic( - _: logging.Logger, __: str, event_dict: EventDict -) -> str: - """ - The *event_dict* is serialized to a json string, so that in New Relic logs - the nested keys will show up as attributes. - """ - return safe_json_dumps(event_dict) - - -def structlog_inject_context_dict(test, level, event_dict): - """ - Add the structlog context dict to log events generated by the stdlib logging library. - """ - context_class = structlog.get_config().get("context_class") - - if context_class: - for key, value in context_class().items(): - if key not in event_dict: - event_dict[key] = value - - return event_dict - - class HourUserRateThrottle(UserRateThrottle): scope = "hour-throttle" diff --git a/trufflehog-allow.json b/trufflehog-allow.json index a183a7c5..ec85115f 100644 --- a/trufflehog-allow.json +++ b/trufflehog-allow.json @@ -6,6 +6,7 @@ "ignore hash 5": "1LhwZ0DvP4cGBgbBdCfaBQV7eiaOc4jWKdzO9WEXLFT7AaqBN6jqd0uyaZeAZ19K", "ignore hash 6": "A035C8C19219BA821ECEA86B64E628F8D684696D", "ignore hash 7": "96334b4eb6a7ae5b0d86abd7febcbcc67323bb94", + "ignore hash 8": "MTgwMTYwfEFQTXxBUFBMSUNBVElPTnwxMDQ5Njk0MDU0", "json base64 content": "regex:\"content\": \"", "img base64 content": "regex:data:image/png;base64,.*", "sentry url": "https://2df6096a4fd94bd6b4802124d10e4b8d@o8544.ingest.sentry.io/4504157846372352",