import logging
import pytest

from .. import context_pb2
from .. import monitoring_pb2
from ..monitoring_client import MonitoringClient
from ..monitoring_server import start_server, stop_server

LOGGER = logging.getLogger(__name__)
LOGGER.setLevel(logging.DEBUG)

SERVER_ADDRESS = '127.0.0.1'
LISTEN_ADDRESS = '[::]'
PORT = 7070

###########################
# Tests Setup
###########################

# This fixture will be requested by test cases and last during testing session
@pytest.fixture(scope='session')
def monitoring_service():
    LOGGER.warning('monitoring_service begin')

    LOGGER.info('Initializing MonitoringService...')
    server = start_server(address=LISTEN_ADDRESS, port=PORT)

    # yield the server, when test finishes, execution will resume to stop it
    LOGGER.warning('monitoring_service yielding')
    yield server

    LOGGER.info('Terminating MonitoringService...')
    stop_server(server)


# This fixture will be requested by test cases and last during testing session.
# The client requires the server, so client fixture has the server as dependency.
@pytest.fixture(scope='session')
def monitoring_client(monitoring_service):
    LOGGER.warning('monitoring_client begin')
    client = MonitoringClient(server=SERVER_ADDRESS, port=PORT)  # instantiate the client
    LOGGER.warning('monitoring_client returning')
    return client

# This fixture will be requested by test cases and last during testing session.
@pytest.fixture(scope='session')
def kpi():
    LOGGER.warning('test_include_kpi begin')
    # form request
    kpi = monitoring_pb2.Kpi()
    kpi.kpi_id.kpi_id.uuid = 'KPIID0000'  # pylint: disable=maybe-no-member
    kpi.kpiDescription = 'KPI Desc'
    return kpi


###########################
# Tests Implementation
###########################

# Test case that makes use of client fixture to test server's IncludeKpi method
def test_include_kpi(monitoring_client,kpi):
    # make call to server
    LOGGER.warning('test_include_kpi requesting')
    response = monitoring_client.IncludeKpi(kpi)
    LOGGER.debug(str(response))
    assert isinstance(response, context_pb2.Empty)

# You can add as many tests as you want. Just copy the "def test_include_kpi(monitoring_client):" and implement
# appropriate tests. monitoring_client and monitoring_service fixtures and their connection are reused along tests.

# Test case that makes use of client fixture to test server's MonitorKpi method
def test_monitor_kpi(monitoring_client,kpi):
    LOGGER.warning('test_monitor_kpi begin')
    response = monitoring_client.MonitorKpi(kpi)
    LOGGER.debug(str(response))
    assert isinstance(response, context_pb2.Empty)

# Test case that makes use of client fixture to test server's GetStreamKpi method
def test_getstream_kpi(monitoring_client,kpi):
    LOGGER.warning('test_getstream_kpi begin')
    response = monitoring_client.GetStream_kpi(kpi)
    LOGGER.debug(str(response))
    #assert isinstance(response, monitoring_pb2.Kpi)

# Test case that makes use of client fixture to test server's GetInstantKpi method
def test_getinstant_kpi(monitoring_client,kpi):
    LOGGER.warning('test_getinstant_kpi begin')
    response = monitoring_client.GetInstantKpi(kpi)
    LOGGER.debug(str(response))
    assert isinstance(response, monitoring_pb2.Kpi)
