#// Copyright (c) 2000-2017 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 unittest, json, time, os
import Microservices.Playlist
from Microservices.Playlist.ScheduledPlaylist import ScheduledPlaylist
from test.utils.Utils import *

def loadPlaylist(path):
    with open(path, 'r') as f:
        playlist = json.load(f)
    return playlist

class ScheduledPlaylistTest(unittest.TestCase):

    def setUp(self):
        self.next = 0
        self.failed = False
        self.reason = ''

    def test_requestHandlingWithConditionTrue(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_requestHandlingWithConditionTrue
        Tested component: ServiceFramework
        Feature: ServiceFramework - ScheduledPlaylist
        Requirement: playlist execution
        Action_To_Be_taken:
            execute the playlist and check expected behaviour
        Expected_Result: pass
        '''

        self.expected = (
            (
                lambda type, url, credentials: (type, url, credentials['username']),
                ('LOGIN', 'http://localhost:8000/api.appagent', 'admin'),
                None
            ),
            (
                lambda type, url, requests: (type, url, requests[0]['getData']['filter']),
                ('REQUEST', 'http://localhost:8000/api.appagent', {'dataValue': 'false'}),
                {'contentList': [{'node': {'val': '1', 'tp': 1}}]}
            ),
            (
                lambda type, amount: (type, amount),
                ('WAIT', 0.2),
                None
            ),
            (
                lambda type, url, requests: (type, url, requests[0]['setData']['element']),
                ('REQUEST', 'http://localhost:8000/api.appagent', 'string'),
                {'contentList': [{'node': {'val': '1', 'tp': 1}}]}
            ),
            (
                lambda type: type,
                'LOGOUT',
                None
            )
        )

        self.runPlaylist(PLAYLIST_DIR + '/Playlists/admin/simple.json', 'blue')

    def test_relativeTo(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_relativeTo
        Tested component: ServiceFramework
        Feature: ServiceFramework - ScheduledPlaylist
        Requirement: playlist execution
        Action_To_Be_taken:
            execute the playlist and check expected behaviour
        Expected_Result: pass
        '''

        self.expected = (
            (
                lambda type, url, credentials: (type, url, credentials['username']),
                ('LOGIN', 'http://localhost:8000/api.appagent', 'admin'),
                None
            ),
            (
                lambda type, url, requests: (time.sleep(0.1), requests[0]['setData']['content']),
                (None, 'new_str1'),
                {'contentList': [{'node': {'val': '1', 'tp': 1}}]}
            ),
            (
                lambda type, url, requests: (time.sleep(0.1), requests[0]['setData']['content']),
                (None, 'new_str2'),
                {'contentList': [{'node': {'val': '1', 'tp': 1}}]}
            ),
            (
                lambda type, url, requests: (time.sleep(0.1), requests[0]['setData']['content']),
                (None, 'new_str3'),
                {'contentList': [{'node': {'val': '1', 'tp': 1}}]}
            ),
            (
                lambda type: type,
                'LOGOUT',
                None
            )
        )

        self.runPlaylist(PLAYLIST_DIR + '/Playlists/admin/relativeto.json', 'blue')

    def test_conditionMaxTriesExceeded(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_conditionMaxTriesExceeded
        Tested component: ServiceFramework
        Feature: ServiceFramework - ScheduledPlaylist
        Requirement: playlist execution
        Action_To_Be_taken:
            execute the playlist and check expected behaviour
        Expected_Result: pass
        '''

        self.expected = (
            (
                lambda type, url, credentials: (type, url, credentials['username']),
                ('LOGIN', 'http://localhost:8000/api.appagent', 'admin'),
                None
            ),
            (
                lambda type, url, requests: (type, url, requests[0]['getData']['filter']),
                ('REQUEST', 'http://localhost:8000/api.appagent', {'dataValue': 'false'}),
                {'contentList': [{'node': {'val': '', 'tp': 0}}]}
            ),
            (
                lambda type, amount: (type, amount),
                ('WAIT', 0.1),
                None
            ),
            (
                lambda type, url, requests: (type, url, requests[0]['getData']['filter']),
                ('REQUEST', 'http://localhost:8000/api.appagent', {'dataValue': 'false'}),
                {'contentList': [{'node': {'val': '', 'tp': 0}}]}
            ),
            (
                lambda type, amount: (type, amount),
                ('WAIT', 0.1),
                None
            ),
            (
                lambda type, url, requests: (type, url, requests[0]['getData']['filter']),
                ('REQUEST', 'http://localhost:8000/api.appagent', {'dataValue': 'false'}),
                {'contentList': [{'node': {'val': '', 'tp': 0}}]}
            ),
            (
                lambda type: type,
                'LOGOUT',
                None
            )
        )

        self.runPlaylist(PLAYLIST_DIR + '/Playlists/admin/try.json', 'red')

    def test_conditionsMaxTimeExceeded(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_conditionsMaxTimeExceeded
        Tested component: ServiceFramework
        Feature: ServiceFramework - ScheduledPlaylist
        Requirement: playlist execution
        Action_To_Be_taken:
            execute the playlist and check expected behaviour
        Expected_Result: pass
        '''

        self.expected = (
            (
                lambda type, url, credentials: (type, url, credentials['username']),
                ('LOGIN', 'http://localhost:8000/api.appagent', 'admin'),
                None
            ),
            (
                lambda type, url, requests: time.sleep(0.5),
                None,
                {'contentList': [{'node': {'val': '', 'tp': 0}}]}
            ),
            (
                lambda type: type,
                'LOGOUT',
                None
            )
        )

        self.runPlaylist(PLAYLIST_DIR + '/Playlists/admin/wait.json', 'red')

    def test_stop(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_stop
        Tested component: ServiceFramework
        Feature: ServiceFramework - ScheduledPlaylist
        Requirement: playlist execution
        Action_To_Be_taken:
            execute the playlist and check expected behaviour
        Expected_Result: pass
        '''

        self.expected = (
            (
                lambda type, url, credentials: (type, url, credentials['username']),
                ('LOGIN', 'http://localhost:8000/api.appagent', 'admin'),
                None
            ),
            (
                lambda type, url, requests: self.handler.stop(),
                None,
                {'contentList': [{'node': {'val': '', 'tp': 0}}]}
            ),
            (
                lambda type: type,
                'LOGOUT',
                None
            )
        )

        self.runPlaylist(PLAYLIST_DIR + '/Playlists/admin/relativeto.json', 'black')

    def test_pause(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_pause
        Tested component: ServiceFramework
        Feature: ServiceFramework - ScheduledPlaylist
        Requirement: playlist execution
        Action_To_Be_taken:
            start the playlist
            pause the playlist
            check if the playlist was paused
            resume the playlist
            check if it was resumed
            stop the playlist
        Expected_Result: pass
        '''

        # we count the number of 'actions'; when paused, the counter should not change
        count = [0] # we can't modify an outer variable directly...

        def magicHandler(*args):
            count[0] += 1
            time.sleep(0.1)
            return {'contentList': [{'node': {'val': '', 'tp': 0}}]}

        # start the playlist
        self.handler = ScheduledPlaylist(loadPlaylist(PLAYLIST_DIR + '/Playlists/admin/longtry.json'))
        self.handler._login = magicHandler
        self.handler._logout = magicHandler
        self.handler._wait = magicHandler
        self.handler._sendRequestsToUrl = magicHandler
        self.handler.start(ADMIN)

        # pause the playlist
        time.sleep(0.5)
        self.handler.pause()
        # check if the playlist was paused
        time.sleep(0.2)
        currentCount = count[0]
        time.sleep(0.5)
        self.assertEqual(count[0], currentCount, 'there should be no calls when paused') # there were no additional calls
        # resume the playlist
        self.handler.pause()
        # check if it was resumed
        time.sleep(0.5)
        self.assertNotEqual(count[0], currentCount, 'there should be calls when unpaused') # there were calls after unpause
        # stop the playlist
        self.handler.stop()
        time.sleep(0.2)

    def startPlaylist(self, fileName):
        self.handler = ScheduledPlaylist(loadPlaylist(fileName))
        self.handler._login = self.mockedLogin
        self.handler._logout = self.mockedLogout
        self.handler._wait = self.mockedWait
        self.handler._sendRequestsToUrl = self.mockedSendRequest
        self.handler.start(ADMIN)

    def runPlaylist(self, fileName, color, timeout = 1):
        self.startPlaylist(fileName)
        startTime = time.time()
        while self.handler.isRunning():
            if time.time() - startTime > timeout:
                self.fail('Playlist execution timed out')
            time.sleep(0.1)
        while color not in self.handler.getStatus()['node']['val']:
            if time.time() - startTime > timeout:
                self.fail('Playlist status is wrong, expected ' + color + ', got ' + self.handler.getStatus()['node']['val'])
            time.sleep(0.1)
        if self.failed:
            self.fail(self.reason)

    def handle(self, *args):
        time.sleep(0.1) # this is needed to imitate non-blocking behaviour (this is the only way we can check the status led color reliably)
        if self.next >= len(self.expected):
            self.failed = True
            self.reason = 'Too few expected values: ' + str(len(self.expected))
            return None
        if len(self.expected[self.next]) < 3:
            self.failed = True
            self.reason = 'Not all 3 arguments present, only got: ' + str(len(self.expected[self.next]))
            return None
        transformer, expected, returnValue = self.expected[self.next]
        self.next += 1
        try:
            self.assertEqual(transformer(*args), expected)
        except Exception as e:
            self.failed = True
            self.reason = e
        return returnValue

    def mockedLogin(self, opener, url, userCredentials):
        return self.handle('LOGIN', url, userCredentials)

    def mockedLogout(self):
        return self.handle('LOGOUT')

    def mockedWait(self, amount):
        return self.handle('WAIT', amount)

    def mockedSendRequest(self, opener, url, requests):
        return self.handle('REQUEST', url, requests)

class PlaylistTest(unittest.TestCase):

    def magicHandler(self, *args):
        # a function that mocks parts of the ScheduledPlaylist
        time.sleep(0.1)
        return {'contentList': [{'node': {'val': '', 'tp': 0}}]}

    def createPlaylistExecutor(self, descriptor):
        # create a mocked ScheduledPlaylist
        executor = ScheduledPlaylist(descriptor)
        executor._login = self.magicHandler
        executor._logout = self.magicHandler
        executor._wait = self.magicHandler
        executor._sendRequestsToUrl = self.magicHandler
        return executor

    def setUp(self):
        # the "microservice" under test
        self.handler = Microservices.Playlist.createHandler(PLAYLIST_DIR)
        # the datasource handlers of the microservice
        self.datasourceHandlers = self.handler.getDataSourceHandlers()
        # mock the creation of ScheduledPlaylist
        self.handler._createPlaylistExecutor = self.createPlaylistExecutor
        # a list of created files to delete at the end
        self.created = []

    def tearDown(self):
        # close tested "microservice"
        self.handler.close()
        # delete the created files
        for fileName in self.created:
            if os.path.exists(fileName):
                os.unlink(fileName)

    def test_playlistHandling(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_playlistHandling
        Tested component: ServiceFramework
        Feature: ServiceFramework - Playlist
        Requirement: playlist microservice request handling
        Action_To_Be_taken:
            start a playlist
            check elements of a running and an idle playlist
            pause the running playlist
            check status led
            resume playlist
            check status led
            stop playlist
            check status led
        Expected_Result: pass
        '''

        # start a playlist
        self.set('Start', '0', 1, 'admin/longtry')
        time.sleep(0.2)
        # check elements of a running and an idle playlist
        self.check('0', 'Start', 'admin/longtry')
        self.check('0', 'Start', 'admin/try')
        self.check('0', 'Stop', 'admin/longtry')
        self.check('0', 'Stop', 'admin/try')
        self.check('0', 'Pause', 'admin/longtry')
        self.check('0', 'Pause', 'admin/try')
        self.check('0', 'Start', 'admin/longtry')
        self.check('0', 'Start', 'admin/try')
        self.check('green', 'Status', 'admin/longtry')
        self.check('blue', 'Status', 'admin/try')
        # pause the running playlist
        self.set('Pause', '0', 1, 'admin/longtry')
        time.sleep(0.2)
        # check status led
        self.check('yellow', 'Status', 'admin/longtry')
        # resume playlist
        self.set('Pause', '0', 1, 'admin/longtry')
        time.sleep(0.2)
        # check status led
        self.check('green', 'Status', 'admin/longtry')
        # stop playlist
        self.set('Stop', '0', 1, 'admin/longtry')
        time.sleep(0.2)
        # check status led
        self.check('black', 'Status', 'admin/longtry')

    def test_playlistFileHandling(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_playlistFileHandling
        Tested component: ServiceFramework
        Feature: ServiceFramework - Playlist
        Requirement: playlist microservice file handling
        Action_To_Be_taken:
            create a playlist
            check if it was created
            check if the descriptor is the same as the one that was saved
            delete the playlist
            check that it no longer exists
        Expected_Result: pass
        '''

        # create a playlist
        self.created.append(PLAYLIST_DIR + '/Playlists/admin/test.json')
        self.set('Descriptor', '[]', 4, 'admin/test')
        # check if it was created
        self.assertIn('admin/test', self.makeList(self.get('Playlists')))
        # check if the descriptor is the same as the one that was saved
        self.check('[]', 'Descriptor', 'admin/test')
        # delete the playlist
        self.set('Delete', '1', 1, 'admin/test')
        # check that it no longer exists
        self.assertNotIn('admin/test', self.makeList(self.get('Playlists')))

    def test_microService(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_microService
        Tested component: ServiceFramework
        Feature: ServiceFramework - Playlist
        Requirement: playlist behaviour as a microservice
        Action_To_Be_taken:
            invoke the request handler with a simple request and check the result
        Expected_Result: pass
        '''

        response = getEmptyResponse()
        self.handler.handleMessage('POST', 'api.playlist', {}, '''{
            "requests": [
                {
                    "getData": {
                        "source": "Playlist",
                        "element": "Playlists"
                    }
                }
            ]
        }''', ADMIN, response)
        playlists = self.makeList(json.loads(response['body'])['contentList'][0])
        self.assertIn('admin/longtry', playlists)

    def test_help(self):
        '''
        Author: EDNIGBO Daniel Gobor
        Testcase: test_help
        Tested component: ServiceFramework
        Feature: ServiceFramework - Playlist
        Requirement: datasource help in Playlist
        Action_To_Be_taken:
            get help
            check help syntax
        Expected_Result: pass
        '''

        # get help
        help = self.get('help')['node']['val']
        # check help syntax
        json.loads(help.decode('hex'))

    def makeList(self, response):
        return [element['node']['val'] for element in response['list']]

    def check(self, expected, element, playlist = None, user = ADMIN):
        response = self.get(element, playlist, user)
        self.assertIn(expected, response['node']['val'])

    def get(self, element, playlist = None, user = ADMIN):
        request = {
            'source': self.handler.SOURCE_ID,
            'element': element,
            'params': []
        }
        if playlist is not None:
            request['params'].append({
                'paramName': 'Playlist',
                'paramValue': playlist
            })
        return self.datasourceHandlers[self.handler.SOURCE_ID]['getDataHandler'](request, user)

    def set(self, element, content, tp, playlist = None, user = ADMIN):
        request = {
            'source': self.handler.SOURCE_ID,
            'element': element,
            'params': [],
            'tp': tp,
            'content': content
        }
        if playlist is not None:
            request['params'].append({
                'paramName': 'Playlist',
                'paramValue': playlist
            })
        return self.datasourceHandlers[self.handler.SOURCE_ID]['setDataHandler'](request, user)
