# -*- coding: utf-8 -*-
from __future__ import unicode_literals

import json
import logging
import takeout.takeout_tools as takeout_tools

from django.http import HttpResponse, HttpResponseBadRequest, HttpResponseForbidden
from django.contrib.auth.models import User
from django.views.decorators.csrf import csrf_exempt
from common.models import Job
from takeout.tvm_ticketer import Ticketer


def get_results(request):
    """
    curl -X POST "https://your-service.yandex.net/api/some-url"
        -d "uid=123&unixtime=123456789" -H "X-Ya-Service-Ticket: smth"
    Ответ:
        -   {"status": "ok",
            # мелкие файлы (если счёт на мегабайты - ок), разбитые сразу по имени и содержимому.
            " data": {
                "foo.json": "данные",  # данные в виде строки, если это json, то пусть уже будет сериализован в строку
                "bar.csv": "данные"
                }
            },
        - {"status": "no_data"} # Если уже досрочно известно, что для пользователя не будет данных
    """

    tvm_client = Ticketer()

    # If tvm check failed - return 403
    incoming_ticket = ''
    headers = request.META
    for item in headers.keys():
        if 'YA_SERVICE_TICKET' in item:
            incoming_ticket = headers[item]

    tvm_incoming_check = tvm_client.check_ticket(incoming_ticket)
    if not tvm_incoming_check:
        response = HttpResponseForbidden(
            json.dumps({'status': 'error', 'message': 'no valid tvm ticket found'}),
            content_type='application/json'
        )
        response['X_Ya_Service_Ticket'] = tvm_client.get_ticket('overload')
        return response

    # Every request must contain uid
    uid = request.POST.get('uid')
    if not uid:
        response = HttpResponseBadRequest(
            json.dumps({'status': 'error', 'message': 'no uid is given'}),
            content_type='application/json'
        )
        response['X_Ya_Service_Ticket'] = tvm_client.get_ticket('overload')
        return response

    # Create takeout job for this uid
    collected_results = takeout_tools.collect_data(uid=uid)
    if not collected_results:
        data = {'status': 'no_data'}
    else:
        tests = 'test_id;start_date;test_link\n' + '\n'.join(collected_results)
        data = {'status': 'ok', 'data': {'overload.csv': tests}}

    # Return job_id to takeout
    response = HttpResponse()
    response.content = json.dumps(data)
    response.content_type = 'application/json'
    response['X-Ya-Service-Ticket'] = tvm_client.get_ticket('overload')
    return response


def get_user_status(request):
    blackbox_service_ticket, takeout_service_ticket, error = takeout_tools.get_tvm_tickets()
    if error:
        return takeout_tools.send_response(result='error', code='Internal Error', message=error)

    request_id, user_ticket, error = takeout_tools.check_takeout_request(request)
    if error:
        return takeout_tools.send_response(message=error, tvm_ticket=takeout_service_ticket)

    yandex_uid = takeout_tools.get_user_id_from_blackbox(user_ticket, blackbox_service_ticket)
    if not yandex_uid:
        return takeout_tools.send_response(result='error', code='Internal Error', message='Failed to get yandex_uid', tvm_ticket=takeout_service_ticket)
    else:
        logging.info('Request %s. Search status of the user by yandex_uid %s', request_id, yandex_uid)

    try:
        i = 0
        yandex_user = None
        query = 'select au.id, email, is_active from auth_user as au inner join social_auth_usersocialauth as sa on au.id = sa.user_id and sa.uid = \'{}\''.format(yandex_uid)
        for user in User.objects.raw(query):
            i += 1
            yandex_user = user
        if i == 0:
            raise User.DoesNotExist
        elif i > 1:
            raise User.MultipleObjectsReturned
        elif yandex_user.is_active:
            logging.info('Request %s. User by yandex_uid %s is found and can be deleted.', request_id, yandex_uid)
            return takeout_tools.send_response(result='status', code='ready_to_delete', tvm_ticket=takeout_service_ticket)
        else:
            logging.info('Request %s. User by yandex_uid %s is found and is deleting now.', request_id, yandex_uid)
            return takeout_tools.send_response(result='status', code='delete_in_progress', tvm_ticket=takeout_service_ticket)

    except User.MultipleObjectsReturned:
        logging.error('Request %s. More than one user was found with the yandex_uid %s.', request_id, yandex_uid)
        return takeout_tools.send_response(result='error', code='Internal Error', message='The user has been found, but cannot be deleted. Please, contact the load group.', tvm_ticket=takeout_service_ticket)

    except User.DoesNotExist:
        logging.info('Request %s. User by yandex_uid %s is not found.', request_id, yandex_uid)
        return takeout_tools.send_response(result='status', code='empty', tvm_ticket=takeout_service_ticket)

    except Exception:
        logging.error('Request %s. Failed to get user status. %s', request_id, exc_info=True)
        return takeout_tools.send_response(result='status', code='empty', tvm_ticket=takeout_service_ticket)


@csrf_exempt
def delete_user_data(request):
    blackbox_service_ticket, takeout_service_ticket, error = takeout_tools.get_tvm_tickets()
    if error:
        return takeout_tools.send_response(result='error', code='Internal Error', message=error)

    request_id, user_ticket, error = takeout_tools.check_takeout_request(request)
    if error:
        return takeout_tools.send_response(message=error, tvm_ticket=takeout_service_ticket)

    try:
        assert ['user_data'] == json.loads(request.body.encode('utf-8'))['id']
    except Exception:
        logging.error('Request %s. Unknown user data type to delete. %s', request_id, request.body.encode('utf-8'), exc_info=True)
        return takeout_tools.send_response(message='Unknow user data type', tvm_ticket=takeout_service_ticket)

    yandex_uid = takeout_tools.get_user_id_from_blackbox(user_ticket, blackbox_service_ticket)
    if not yandex_uid:
        return takeout_tools.send_response(result='error', code='Internal Error', message='Failed to get yandex_uid', tvm_ticket=takeout_service_ticket)
    else:
        logging.info('Request %s. Delete data of the user by yandex_uid %s', request_id, yandex_uid)

    try:
        i = 0
        user_id = None
        query = 'select au.id, email, is_active from auth_user as au inner join social_auth_usersocialauth as sa on au.id = sa.user_id and sa.uid = \'{}\''.format(yandex_uid)
        for user in User.objects.raw(query):
            i += 1
            user_id = user.id
        if i > 1:
            raise Exception('Multiple social users are found with uid {}'.format(yandex_uid))
        for user in User.objects.filter(id=user_id):
            user.is_active = False
            user.save()
        for job in Job.objects.filter(user=user_id):
            job.is_deleted = True
            job.save()

    except Exception:
        logging.error('Request %s. Failed to get user_id from social users.', request_id, exc_info=True)
        return takeout_tools.send_response(result='error', code='Internal Error', message='User was not found', tvm_ticket=takeout_service_ticket)

    return takeout_tools.send_response(result='data_deleted', tvm_ticket=takeout_service_ticket)
