#// Copyright (c) 2000-2019 Ericsson Telecom AB                                                         //
#// All rights reserved. This program and the accompanying materials are made available under the terms //
#// of the Eclipse Public License v2.0 which accompanies this distribution, and is available at         //
#// https://www.eclipse.org/org/documents/epl-2.0/EPL-2.0.html                                                           //
#/////////////////////////////////////////////////////////////////////////////////////////////////////////
import json, uuid, logging
from Common.DsRestAPI import DsRestAPI
from LdapAuthenticator import authenticate
from FileUserHandler import FileUserHandler as UserHandler
from Help import DSHELP

class AuthenticationHandler:
    '''
    This class handles the authentication and user groups
    Requests coming to login/api.authenticate are used for logging in.
    Requests coming to logout/api.authenticate are used for logging out.
    DsRestAPI requests can be used to edit the user groups.
    AppAgent can use the getUserCredentials public function to get the user credentials of the current user.
    '''

    SOURCE_ID = 'Authentication'

    def __init__(self, directory):
        self._sessionDb = {}
        self._userHandler = UserHandler(directory)
        self._logger = logging.getLogger(__name__)
        self._dsRestAPI = DsRestAPI(self._getDataHandler, self._setDataHandler)

    def _login(self, body):
        authenticate(body['username'], body['password'])
        sessionId = str(uuid.uuid4())
        groups = self._userHandler.getUserGroups(body['username'])
        self._sessionDb[sessionId] = {'username': body['username'], 'password': body['password'], 'groups': groups}
        return sessionId

    def _getSessionIdFromHeaders(self, headers):
        cookieHeader = headers.get('cookie')
        sessionId = None
        if cookieHeader != None:
            for cookie in cookieHeader.split(';'):
                if cookie.strip().startswith('PYSESSID='):
                    sessionId = cookie.strip().replace('PYSESSID=', '')
                    break
        return sessionId

    def getUserCredentials(self, headers):
        sessionId = self._getSessionIdFromHeaders(headers)
        if sessionId in self._sessionDb:
            return self._sessionDb[sessionId]
        else:
            return {'username': None, 'password': None, 'groups': set([])}

    def _getDataHandler(self, request, userCredentials):
        element = request['element']
        params = request['params']

        if element == 'help':
            help = {'sources': [{'source': self.SOURCE_ID, 'dataElements': DSHELP}]}
            return {'node': {'val': json.dumps(help).encode('hex'), 'tp': 5}}
        elif element == 'ListGroups':
            return {'list': [{'node': {'val': group, 'tp': 10}} for group in self._userHandler.listGroups()]}
        elif element == 'ListUsersInGroup' and len(params) == 1 and params[0]['paramName'] == 'Group':
            return {'list': [{'node': {'val': user, 'tp': 10}} for user in self._userHandler.listUsersInGroup(params[0]['paramValue'])]}
        elif element == 'ListGroupsOfUser' and len(params) == 1 and params[0]['paramName'] == 'User':
            return {'list': [{'node': {'val': group, 'tp': 10}} for group in self._userHandler.getUserGroups(params[0]['paramValue'])]}
        elif element in ['RemoveGroup', 'RemoveUserFromGroup']:
            return {'node': {'val': '0', 'tp': 1}}
        elif element in ['AddGroup', 'AddUserToGroup']:
            return {'node': {'val': '0', 'tp': 4}}

    def _setDataHandler(self, request, userCredentials):
        element = request['element']
        params = request['params']
        content = request['content']
        tp = request['tp']

        if 'admin' in userCredentials['groups']:
            if element == 'AddGroup':
                self._userHandler.addGroup(content)
                return {'node': {'val': content, 'tp': tp}}
            elif element == 'RemoveGroup' and len(params) == 1 and params[0]['paramName'] == 'Group':
                self._userHandler.removeGroup(params[0]['paramValue'])
                return {'node': {'val': '0', 'tp': 1}}
            elif element == 'AddUserToGroup' and len(params) == 1 and params[0]['paramName'] == 'Group':
                self._userHandler.addUserToGroup(content, params[0]['paramValue'])
                return {'node': {'val': content, 'tp': tp}}
            elif element == 'RemoveUserFromGroup' and len(params) == 2 and params[0]['paramName'] == 'User' and params[1]['paramName'] == 'Group':
                self._userHandler.removeUserFromGroup(params[0]['paramValue'], params[1]['paramValue'])
                return {'node': {'val': '0', 'tp': 1}}

    def handleMessage(self, method, path, headers, body, userCredentials, response):
        if path.startswith('login'):
            try:
                loginInfo = json.loads(body)
                sessionId = self._login(loginInfo)
                response['returnCode'] = 200
                # increase the year when needed
                response['headers']['Set-Cookie'] = 'PYSESSID=' + sessionId + '; Path=/; expires=Thu, 01 Jan 2070 00:00:00 UTC;'
                self._logger.info('Login ' + sessionId + ' ' + loginInfo['username'])
            except Exception as e:
                self._logger.exception('Failed to login')
                response['returnCode'] = 401
                response['body'] = str(e)
        elif path.startswith('logout'):
            try:
                sessionId = self._getSessionIdFromHeaders(headers)
                self._sessionDb.pop(sessionId, None)
                response['returnCode'] = 200
                response['headers']['Set-Cookie'] = 'PYSESSID=' + '; Path=/; expires=Thu, 01 Jan 1970 00:00:00 UTC;'
                self._logger.info('Logout ' + sessionId + ' ' + str(userCredentials['username']))
            except Exception as e:
                self._logger.exception('Failed to logout ' + str(userCredentials['username']))
                response['returnCode'] = 400
                response['body'] = str(e)
        else:
            response['body'] = json.dumps(self._dsRestAPI.parseRequest(json.loads(body), userCredentials))
            response['headers']['Content-Type'] = 'application/json'

    def getDataSourceHandlers(self):
        return {
            self.SOURCE_ID: {
                'getDataHandler': self._getDataHandler,
                'setDataHandler': self._setDataHandler
            }
        }

    def close(self):
        pass