import json
from logging.config import dictConfig

from flask import Flask, Response, jsonify, request

from prometheus_client import (CollectorRegistry, CONTENT_TYPE_LATEST,
                               generate_latest, multiprocess)

from requests.exceptions import ConnectionError as RequestsConnectionError

from sf_notifier.helpers import alert_fields_and_action, create_file
from sf_notifier.salesforce.client import SESSION_FILE, SalesforceClient

from simple_salesforce.exceptions import SalesforceError

from simple_settings import settings


dictConfig(settings.LOGGING)

app = Flask(__name__)

registry = CollectorRegistry()
multiprocess.MultiProcessCollector(registry)

create_file(SESSION_FILE)
sf_cli = SalesforceClient(settings.SF_CONFIG, prometheus_registry=registry)


@app.route('/metrics', methods=['GET'])
def metrics():
    return Response(generate_latest(registry),
                    mimetype=CONTENT_TYPE_LATEST)


@app.route('/info', methods=['GET'])
def info():
    return jsonify({
        'version': settings.VERSION,
        'hashing': sf_cli.hash_func.__name__
    })


@app.route('/hook', methods=['POST'])
def webhook_receiver():

    try:
        data = json.loads(request.data)
    except ValueError:
        msg = 'Invalid request data: {}.'.format(request.data)
        app.logger.error(msg)
        return Response(json.dumps({'error': msg}),
                        status=400,
                        mimetype='application/json')

    app.logger.info('Received requests: {}'.format(data))

    cases = []
    for alert in data['alerts']:
        try:
            alert['labels']['env_id'] = sf_cli.environment
            fields, action = alert_fields_and_action(
                alert,
                add_links=settings.ADD_LINKS,
                cluster_id=settings.CLUSTER_ID)
        except KeyError as key:
            msg = 'Alert misses {} key.'.format(key)
            app.logger.error(msg)
            return Response(json.dumps({'error': msg}),
                            status=400,
                            mimetype='application/json')

        if fields:
            try:
                cases.append(getattr(sf_cli, action)(*fields))
            except (SalesforceError, RequestsConnectionError) as err:
                msg = 'Salesforce request failure: {}.'.format(err)
                sf_cli.metrics['sf_error_count'].inc()
                app.logger.error(msg)
                return Response(json.dumps({'error': msg}),
                                status=500,
                                mimetype='application/json')

    if len(cases) == 1:
        return jsonify(cases[0])
    return jsonify(cases)


if __name__ == '__main__':
    app.run()
