# By: Riasat Ullah
# This file contains Datadog integration related db queries.

from utils import errors, integration_type_names as intt, key_manager, var_names
import datetime
import psycopg2


def get_datadog_account_tokens(conn, timestamp, organization_id, integration_key=None, datadog_oid=None,
                               integration_id=None):
    '''
    Get the account details of a Datadog integration.
    :param conn: db connection
    :param timestamp: timestamp when this request is being made
    :param organization_id: ID of the organization
    :param integration_key: (concealed) integration key of the integration
    :param datadog_oid: (str) Datadog account ID
    :param integration_id: (int) the ID of the integration
    :return: (dict) -> {vendor_endpoint: ..., access_token: ..., refresh_token: ...}
    :errors: AssertionError, DatabaseError
    '''
    assert isinstance(timestamp, datetime.datetime)
    assert isinstance(organization_id, int)

    query_params = {'timestamp': timestamp, 'org_id': organization_id, 'dd_typ': intt.datadog}
    conditions = []
    if integration_key is not None:
        conditions.append(''' external_id in (
            select vendor_endpoint_name from service_integrations
            where start_timestamp <= %(timestamp)s
                and end_timestamp > %(timestamp)s
                and organization_id = %(org_id)s
                and integration_key = %(integ_key)s
        )''')
        query_params['integ_key'] = key_manager.unmask_reference_key(integration_key)
    if datadog_oid is not None:
        assert isinstance(datadog_oid, str)
        conditions.append(' external_id = %(dd_oid)s ')
        query_params['dd_oid'] = datadog_oid
    if integration_id is not None:
        assert isinstance(integration_id, int)
        conditions.append(' integration_id = %(integ_id)s ')
        query_params['integ_id'] = integration_id

    query = '''
            select external_id, details->>'vendor_endpoint', details->>'access_token', details->>'refresh_token'
            from organization_integration_type_details
            where start_timestamp <= %(timestamp)s
                and end_timestamp > %(timestamp)s
                and organization_id = %(org_id)s
                and integration_type_id in (
                    select integration_type_id from integration_types
                    where start_date <= %(timestamp)s
                        and end_date > %(timestamp)s
                        and integration_type = %(dd_typ)s
                )
                {0};
            '''.format(' and ' + ' and '.join(conditions) if len(conditions) > 0 else '')
    try:
        result = conn.fetch(query, query_params)
        if len(result) == 1:
            return {
                var_names.vendor_endpoint_name: result[0][0],
                var_names.vendor_endpoint: result[0][1],
                var_names.access_token: result[0][2],
                var_names.refresh_token: result[0][3]
            }
        elif len(result) == 0:
            raise ValueError(errors.err_unknown_resource)
        else:
            raise SystemError(errors.err_internal_multiple_entries_found)
    except psycopg2.DatabaseError:
        raise
