<commit_before>import functools
import time

import anchore_engine.configuration.localconfig
from anchore_engine.subsys import logger
from anchore_engine.version import version

from prometheus_client import Histogram, Summary, Gauge, Counter
from prometheus_flask_exporter import PrometheusMetrics

enabled = False
flask_metrics = None
flask_metric_name = "flask_http_request_duration_seconds"
metrics = {}

#class anchore_flask_track(object):
#    def __init__(self, enabled, flask_metrics):
#        self.enabled = enabled
#        self.flask_metrics = flask_metrics
#    def __call__(self, func):
#        if self.enabled and self.flask_metrics:
#            import anchore_engine.subsys.metrics
#            timer = time.time()
#            rc = func
#            anchore_engine.subsys.metrics.histogram_observe("anchore_http_request_duration_seconds", time.time() - timer, path=request.path, method=request.method, status=httpcode)
#            return(rc)
#        else:
#            return(func)
            

#class anchore_flask_track(object):
#    def __init__(self):
#        pass
#    def __call__(self, func):
#        from anchore_engine.subsys.metrics import flask_metrics, enabled
#        if enabled:
#            flask_metrics.do_not_track()
#            with flask_metrics.histogram('anchore_http_request_duration_seconds', "", labels={'path': lambda: request.path, 'method': lambda: request.method, 'status': lambda respon#se: response[1]}).time():
#                rc = func
##            #@flask_metrics.do_not_track()
##            #rc = None
##            #with flask_metrics.histogram('anchore_http_request_duration_seconds', "", labels={'path': lambda: request.path, 'method': lambda: request.method, 'status': lambda resp#o#nse: response[1]}).time():
##            #    rc = func
#            return(rc)
#        else:
#            return(func)

class disabled_flask_metrics(object):
    def _call_nop(self):
        def decorator(f):
            @functools.wraps(f)
            def func(*args, **kwargs):
                return f(*args, **kwargs)
            return func
        return decorator
    def do_not_track(self):
        return self._call_nop()
    def counter(self, *args, **kwargs):
        return self._call_nop()
    def gauge(self, *args, **kwargs):
        return self._call_nop()
    def summary(self, *args, **kwargs):
        return self._call_nop()
    def histogram(self, *args, **kwargs):
        return self._call_nop()

def init_flask_metrics(flask_app, export_defaults=True, **kwargs):
    global flask_metrics, enabled

    try:
        localconfig = anchore_engine.configuration.localconfig.get_config()
        metrics_config = localconfig.get('metrics', {})
        enabled = bool(metrics_config.get('enable', False))
    except Exception as err:
        logger.warn("unable to determine if metrics are enabled - exception: " + str(err))
        enabled = False

    if not enabled:
        flask_metrics = disabled_flask_metrics()
        return(True)
    
    if not flask_metrics:
        flask_metrics = PrometheusMetrics(flask_app, export_defaults=export_defaults)
        flask_metrics.info('anchore_service_info', "Anchore Service Static Information", version=version, **kwargs)

    return(True)

def is_enabled():
    global enabled
    return(enabled)

def get_flask_metrics_obj():
    global flask_metrics, enabled

    if not enabled:
        return(True)

    return(flask_metrics)

def get_summary_obj(name, description="", **kwargs):
    global enabled

    if not enabled:
        return(True)

    ret = None
    try:
        if name not in metrics:
            metrics[name] = Summary(name, description, kwargs.keys())
        ret = metrics[name]
    except:
        logger.warn("could not create/get named metric ("+str(name)+")")

    return(ret)

def summary_observe(name, observation, description="", **kwargs):
    global metrics, enabled

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            metrics[name] = Summary(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).observe(observation)
        else:
            metrics[name].observe(observation)

    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)

def histogram_observe(name, observation, description="", buckets=None, **kwargs):
    global metrics, enabled

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            if buckets:
                buckets.append(float("inf"))
                metrics[name] = Histogram(name, description, kwargs.keys(), buckets=buckets)
            else:
                metrics[name] = Histogram(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).observe(observation)
        else:
            metrics[name].observe(observation)
    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)

def gauge_set(name, observation, description="", **kwargs):
    global metrics

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            metrics[name] = Gauge(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).set(observation)
        else:
            metrics[name].set(observation)

    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)

def counter_inc(name, step=1, description="", **kwargs):
    global metrics

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            metrics[name] = Counter(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).inc(step)
        else:
            metrics[name].inc(step)

    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)
<commit_msg>fix bug where metric call would cause failure when metrics are disabled<commit_after>import functools
import time

import anchore_engine.configuration.localconfig
from anchore_engine.subsys import logger
from anchore_engine.version import version

from prometheus_client import Histogram, Summary, Gauge, Counter
from prometheus_flask_exporter import PrometheusMetrics

enabled = False
flask_metrics = None
flask_metric_name = "flask_http_request_duration_seconds"
metrics = {}

#class anchore_flask_track(object):
#    def __init__(self, enabled, flask_metrics):
#        self.enabled = enabled
#        self.flask_metrics = flask_metrics
#    def __call__(self, func):
#        if self.enabled and self.flask_metrics:
#            import anchore_engine.subsys.metrics
#            timer = time.time()
#            rc = func
#            anchore_engine.subsys.metrics.histogram_observe("anchore_http_request_duration_seconds", time.time() - timer, path=request.path, method=request.method, status=httpcode)
#            return(rc)
#        else:
#            return(func)
            

#class anchore_flask_track(object):
#    def __init__(self):
#        pass
#    def __call__(self, func):
#        from anchore_engine.subsys.metrics import flask_metrics, enabled
#        if enabled:
#            flask_metrics.do_not_track()
#            with flask_metrics.histogram('anchore_http_request_duration_seconds', "", labels={'path': lambda: request.path, 'method': lambda: request.method, 'status': lambda respon#se: response[1]}).time():
#                rc = func
##            #@flask_metrics.do_not_track()
##            #rc = None
##            #with flask_metrics.histogram('anchore_http_request_duration_seconds', "", labels={'path': lambda: request.path, 'method': lambda: request.method, 'status': lambda resp#o#nse: response[1]}).time():
##            #    rc = func
#            return(rc)
#        else:
#            return(func)

class disabled_flask_metrics(object):
    def _call_nop(self):
        def decorator(f):
            @functools.wraps(f)
            def func(*args, **kwargs):
                return f(*args, **kwargs)
            return func
        return decorator
    def do_not_track(self):
        return self._call_nop()
    def counter(self, *args, **kwargs):
        return self._call_nop()
    def gauge(self, *args, **kwargs):
        return self._call_nop()
    def summary(self, *args, **kwargs):
        return self._call_nop()
    def histogram(self, *args, **kwargs):
        return self._call_nop()

def init_flask_metrics(flask_app, export_defaults=True, **kwargs):
    global flask_metrics, enabled

    try:
        localconfig = anchore_engine.configuration.localconfig.get_config()
        metrics_config = localconfig.get('metrics', {})
        enabled = bool(metrics_config.get('enable', False))
    except Exception as err:
        logger.warn("unable to determine if metrics are enabled - exception: " + str(err))
        enabled = False

    if not enabled:
        flask_metrics = disabled_flask_metrics()
        return(True)
    
    if not flask_metrics:
        flask_metrics = PrometheusMetrics(flask_app, export_defaults=export_defaults)
        flask_metrics.info('anchore_service_info', "Anchore Service Static Information", version=version, **kwargs)

    return(True)

def is_enabled():
    global enabled
    return(enabled)

def get_flask_metrics_obj():
    global flask_metrics, enabled
    if not enabled:
        return(None)
    return(flask_metrics)

def get_summary_obj(name, description="", **kwargs):
    global metrics, enabled

    if not enabled:
        return(None)

    ret = None
    try:
        if name not in metrics:
            metrics[name] = Summary(name, description, kwargs.keys())
        ret = metrics[name]
    except:
        logger.warn("could not create/get named metric ("+str(name)+")")

    return(ret)

def summary_observe(name, observation, description="", **kwargs):
    global metrics, enabled

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            metrics[name] = Summary(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).observe(observation)
        else:
            metrics[name].observe(observation)

    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)

def histogram_observe(name, observation, description="", buckets=None, **kwargs):
    global metrics, enabled

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            if buckets:
                buckets.append(float("inf"))
                metrics[name] = Histogram(name, description, kwargs.keys(), buckets=buckets)
            else:
                metrics[name] = Histogram(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).observe(observation)
        else:
            metrics[name].observe(observation)
    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)

def gauge_set(name, observation, description="", **kwargs):
    global metrics

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            metrics[name] = Gauge(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).set(observation)
        else:
            metrics[name].set(observation)

    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)

def counter_inc(name, step=1, description="", **kwargs):
    global metrics

    if not enabled:
        return(True)

    try:
        if name not in metrics:
            metrics[name] = Counter(name, description, kwargs.keys())

        if kwargs:
            metrics[name].labels(**kwargs).inc(step)
        else:
            metrics[name].inc(step)

    except Exception as err:
        logger.warn("adding metric failed - exception: " + str(err))
        
    return(True)

{'fraction_non_alphanumeric': 0.10943023925018498, 'fraction_numerical': 0.0004932993504891886, 'mean_word_length': 2.658345864661654, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6590566', 'n_tokens_mistral': 3500, 'n_tokens_neox': 3413, 'n_words': 836}