//
// Copyright (c) 2009-2010 Ronald Kluth
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
//

/**
 * @file TestChannelManager.cpp
 * @author Ronald Kluth
 * @date created at 2010/04/17
 * @brief Unit tests for class template Channel
 * @since 0.1
 */

#include "global.h"
#include <string>

SUITE( CppLogUnitTest )
{
	struct DummyConsumer: public Log::Consumer<>
	{
		virtual void consume( const Log::ChannelId channelId, const Log::Record& record ) {}
	};

	struct ChannelManagerFixture
	{
		typedef Log::Channel<> Channel;
		typedef std::tr1::shared_ptr< Channel > ChannelPtr;
		typedef DummyConsumer Consumer;
		typedef std::tr1::shared_ptr< Consumer > ConsumerPtr;
		typedef Log::Filter<> Filter;
		typedef std::tr1::shared_ptr< Filter > FilterPtr;

		ChannelManagerFixture()
		:	manager(  )
		,	id1( 123 )
		,	id2( 456 )
		{}

		Log::ChannelManager<> manager;
		Log::ChannelId id1;
		Log::ChannelId id2;
	};

	TEST( ChannelManagerNameScopeDefaults )
	{
		std::string defaultName = "No label given";
		char defaultSpacer = ' ';
		Log::ChannelManager<> manager( defaultName, defaultSpacer );
		std::string emptyName = manager.createUniqueName( "" );
		std::string emptyName1 = manager.createUniqueName( "" );

		CHECK_EQUAL( defaultName, emptyName );
		CHECK_EQUAL( defaultSpacer, emptyName1[ defaultName.size() ] );
	}

	TEST_FIXTURE( ChannelManagerFixture, GetChannel )
	{
		ChannelPtr c1 = manager.getChannel( id1 );
		CHECK( (bool)c1 );
		ChannelPtr c2 = manager.getChannel( id1 );
		CHECK_EQUAL( c1, c2 );
	}

	TEST_FIXTURE( ChannelManagerFixture, AddConsumer )
	{
		ConsumerPtr con( new Consumer() );
		ChannelPtr c1 = manager.getChannel( id1 );
		manager.addConsumer( id1, con );
		CHECK_EQUAL( 1, c1->getConsumers().size() );
		CHECK( c1->getConsumers().find( con ) != c1->getConsumers().end() );

		ConsumerPtr con2( new Consumer() );
		ChannelPtr c2 = manager.getChannel( id2 );
		manager.addConsumer( con2 );
		CHECK_EQUAL( 2, c1->getConsumers().size() );
		CHECK_EQUAL( 1, c2->getConsumers().size() );
		CHECK( c1->getConsumers().find( con2 ) != c1->getConsumers().end() );
		CHECK( c2->getConsumers().find( con2 ) != c2->getConsumers().end() );
	}

	TEST_FIXTURE( ChannelManagerFixture, RemoveConsumer )
	{
		ConsumerPtr con( new Consumer() );
		ConsumerPtr con2( new Consumer() );
		ChannelPtr c1 = manager.getChannel( id1 );
		ChannelPtr c2 = manager.getChannel( id2 );
		manager.addConsumer( con );
		manager.addConsumer( con2 );
		manager.removeConsumer( id1, con );

		CHECK_EQUAL( 1, c1->getConsumers().size() );
		CHECK( c1->getConsumers().find( con ) == c1->getConsumers().end() );

		manager.removeConsumer( con2 );
		CHECK_EQUAL( 0, c1->getConsumers().size() );
		CHECK_EQUAL( 1, c2->getConsumers().size() );
		CHECK( c1->getConsumers().find( con2 ) == c1->getConsumers().end() );
		CHECK( c2->getConsumers().find( con2 ) == c2->getConsumers().end() );
		CHECK( c2->getConsumers().find( con ) != c1->getConsumers().end() );
	}

	TEST_FIXTURE( ChannelManagerFixture, SetResetFilter )
	{
		FilterPtr filter = Filter::create();
		ChannelPtr c1 = manager.getChannel( id1 );
		ChannelPtr c2 = manager.getChannel( id2 );

		manager.setFilter( id1, filter );
		CHECK_EQUAL( filter, c1->getFilter() );

		manager.setFilter( filter );
		CHECK_EQUAL( filter, c1->getFilter() );
		CHECK_EQUAL( filter, c2->getFilter() );

		manager.resetFilter( id1 );
		CHECK( ! c1->hasFilter() );

		manager.resetFilter();
		CHECK( ! c1->hasFilter() );
		CHECK( ! c2->hasFilter() );
	}
}
