//
// C++ Implementation: c6usersmanager
//
// Description:
//
//
// Author: Giorgio A. <openc6@hotmail.com>, (C) 2005
//
// Copyright: See COPYING file that comes with this distribution
//
//
#include "c6usersmanager.h"
#include <qtextstream.h>

#define C6USER_EXT "@c6.virgilio.it"

static const char* defaultInitialGroupString[] =
{"Amici","Lista Nera","Lista Autorizzati",0
};

C6Users::C6UsersList nullList;

C6UsersManager::C6UsersManager()
{
    _whiteList.setAutoDelete(true);
    addGroup(QString(getDefaultInitialGroupString(LISTA_NERA)));  
}

C6UsersManager::~C6UsersManager()
{
    C6ListHash::Iterator it;
   
    for (it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        it.data().clear();
    }
     
    _c6list.clear();     
}

const char* C6UsersManager::getDefaultInitialGroupString(GROUP_TYPE type)
{
    return(defaultInitialGroupString[type]);
}

/*!
    \fn C6UsersManager::saveNetfriendList()
                save the current nick list  
 */
void C6UsersManager::saveNetfriendList(QTextStream & stream)
{
    QString str;
    C6ListHash::Iterator it;

    for (it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        stream << "[" << it.key() << "]" << "\n";

        for ( C6Users *tmp = it.data().first(); tmp; tmp = it.data().next())
        {
            str =  tmp->getNick().stripWhiteSpace();

            if (str.length() < 16)                        // seems that length > 15 is not allowed
            {
                stream << str << "\n";
            }
        }
    }
}

void C6UsersManager::addUser(QString const & group,QString const & user,QString const & nick)
{
    if ((group.length() > 0) && (nick.length() > 0) && (user.length() > 0))
    {          
        C6ListHash::Iterator it = _c6list.find(group);       
        
        if (it == _c6list.end())
        {
            it = addGroup(group);    
        }      
        
        C6Users *new_item = new C6Users(user,nick);
        it.data().append(new_item);
    }   
}

void C6UsersManager::addUser(QString const & group,QString const & nick)
{
    QString user = nick+C6USER_EXT;     
    addUser(group,user,nick);     
}

void C6UsersManager::removeUser(QString const & nick)
{
    bool found = false;    
    C6ListHash::Iterator it;
    C6Users *tmp = 0;   

    for (it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        for (tmp = it.data().first(); tmp; tmp = it.data().next())
        {
            if (tmp->getNick().compare(nick) == 0)
            {
                found = true;    
                break;
            }    
        }
        
        if (found == true)
        {
            it.data().remove(tmp);         
            break;
        }             
    }
}

QStringList C6UsersManager::getGroupUsers(QString const &group)
{
    QStringList nickList;
    C6ListHash::Iterator it = _c6list.find(group);       
    
    if (it != _c6list.end())   
    {
        for (C6Users *tmp = it.data().first(); tmp; tmp = it.data().next())
        {
            nickList.append(tmp->getNick());     
        }
    }         
    
    return(nickList);
}
 
C6Users* C6UsersManager::getC6UserPtr(const QString &nick)
{
    C6Users *tmp = 0;   
    bool found = false;
        
    for (C6ListHash::Iterator it = _c6list.begin(); (it != _c6list.end()) && (found == false); ++it )
    {
        for (tmp = it.data().first(); tmp; tmp = it.data().next())
        {
            if (tmp->getNick().compare(nick) == 0)
            {
                found = true;    
                break;
            }            
        }
    }        
    
    return(tmp);   
}      

C6Users::C6UsersList& C6UsersManager::getC6UsersFromGroup(QString const &group)
{
    C6ListHash::Iterator it = _c6list.find(group);       
    
    if (it != _c6list.end())   
    {
        return(it.data());         
    }         
    else
    {      
        return(nullList);
    }      
}

void C6UsersManager::setAllUsersOffline()
{
    C6ListHash::Iterator it;

    for (it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        for ( C6Users *tmp = it.data().first(); tmp; tmp = it.data().next())
        {
            tmp->setStatus(C6Users::U_OFFLINE);
            tmp->setMessaged(false); 
        }
    }   
}

QStringList C6UsersManager::getAllUsers()
{
    QStringList nickList;
    QString line;
    C6ListHash::Iterator it;

    for (it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        for (C6Users *tmp = it.data().first(); tmp; tmp = it.data().next())
        {
            line = tmp->getNick().stripWhiteSpace();
            line.remove(QChar(0x0a));
            nickList.append(line);
        }
    }      
    
    return(nickList);
}

bool C6UsersManager::groupIsPresent(QString const &group)
{
    C6ListHash::Iterator it = _c6list.find(group);       
    return((it != _c6list.end()));
}

C6ListHash::Iterator C6UsersManager::addGroup(QString const &group)
{
    C6ListHash::Iterator it = _c6list.find(group);
               
    if (it == _c6list.end())
    {          
        C6Users::C6UsersList *list = new C6Users::C6UsersList;
        list->setAutoDelete(true);   
        it = _c6list.insert(group,*list,FALSE);  
    }      
    
    return(it);    
}

bool C6UsersManager::removeGroup(QString const &group)
{
    bool remove = false;
    
    if (group.compare(QString(getDefaultInitialGroupString(LISTA_NERA))) != 0)
    {          
        C6ListHash::Iterator it = _c6list.find(group);       
        if (it != _c6list.end())
        { 
            if (it.data().count() == 0)
            {
                _c6list.remove(group);    
                remove = true;
            }                                
        }
    }   
    
    return(remove);   
}

QStringList C6UsersManager::getAllGroups()
{
    QStringList groupList;

    for (C6ListHash::Iterator it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        groupList.append(it.key().stripWhiteSpace().remove(QChar(0x0a)));     
    }   
    
    return(groupList);   
}

bool C6UsersManager::isBlackListed(QString const & nick)
{
    bool found = false;
    QString blackGroup = QString(getDefaultInitialGroupString(LISTA_NERA));

    QStringList const list = getGroupUsers(blackGroup);

    for(int i=0; i < list.count(); i++)
    {
        if (list[i].compare(nick) == 0)
        {
            found =  true;
            break;
        }
    }
    
    return(found);
}


/*!
    \fn C6UsersManager::renameGroup(const QString &oldname,const QString &newname)
 */
bool C6UsersManager::renameGroup(const QString &oldname,const QString &newname)
{
    bool renamed = false;

    if ((newname.compare(QString(getDefaultInitialGroupString(LISTA_NERA))) != 0) &&
         (oldname.compare(QString(getDefaultInitialGroupString(LISTA_NERA))) != 0))
    {
        _c6list[newname] = _c6list[oldname];
        _c6list.remove(oldname);     
        renamed = true;    
    }

    return(renamed);
}
   
const QStringList C6UsersManager::getBlackListUsers()
{
   QString blackGroup = QString(getDefaultInitialGroupString(LISTA_NERA));
   return(getGroupUsers(blackGroup));     
}      

const QString C6UsersManager::getBlackListGroupName()
{
    return(QString(getDefaultInitialGroupString(LISTA_NERA)));
}
      
const QString C6UsersManager::getFriendListGroupName()
{
    return(QString(getDefaultInitialGroupString(AMICI)));
}      
      
const QString C6UsersManager::getWhiteListGroupName()
{
    return(QString(getDefaultInitialGroupString(LISTA_AUTORIZZATI)));
}       
      
void C6UsersManager::clear()
{
    C6ListHash::Iterator it;
   
    for (it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        it.data().clear();
    }
     
    _c6list.clear();  
    _whiteList.clear();    
    
    addGroup(QString(getDefaultInitialGroupString(LISTA_NERA)));    
}    
  
C6ListHash & C6UsersManager::getNetfriendList()
{
    return(_c6list);    
}        

const QString C6UsersManager::getUserGroupName(QString const &user)
{
    C6ListHash::Iterator it;
    QString ret;
    
    for (it = _c6list.begin(); it != _c6list.end(); ++it )
    {
        for (C6Users *tmp = it.data().first(); tmp; tmp = it.data().next())
        {
            if (tmp->getNick().compare(user) == 0)
            {
                ret = it.key();
                return(ret);                
            }            
        }
    }    
    
    return(ret);        
}
      
bool C6UsersManager::isTheBlackList(QString const &group)
{
    return(group.compare(QString(getDefaultInitialGroupString(LISTA_NERA))) == 0);   
}    
        
void C6UsersManager::update(C6UsersManager& list)
{
    C6ListHash::Iterator it;
    QStringList groups = list.getAllGroups();        
    
    for(unsigned int j=0; j < groups.count(); j++)
    {
        QStringList users = list.getGroupUsers(groups[j]); 
                
        if (groupIsPresent(groups[j]) == false)
        {
            addGroup(groups[j]);             
        }             
        
        for (unsigned int i=0; i < users.count(); i++)    
        {       
            if (getC6UserPtr(users[i]) == 0)
            {
                addUser(groups[j],users[i]);
            }       
        }             
    }          
}    

/*!
    \fn C6UsersManager::setWhiteList(QStringList const & list)
 */
void C6UsersManager::setWhiteList(QStringList const & list)
{
  //  _whiteList = list;
}


/*!
    \fn C6UsersManager::addToWhiteList(Qstring const &user)
 */
 void C6UsersManager::addToWhiteList(QString const &user,QString const &nick)
{
    if ((nick.length() > 0) && (user.length() > 0))
    {  
        if (isWhiteListed(nick) == false)
        {         
            C6Users *new_item = new C6Users(user,nick);
            _whiteList.append(new_item);
        }         
    }      
}

/*!
    \fn C6UsersManager::addToWhiteList(Qstring const &user)
 */
void C6UsersManager::addToWhiteList(QString const &nick)
{
    addToWhiteList(nick+C6USER_EXT,nick);   
}

/*!
    \fn C6UsersManager::getWhiteListUsers()
 */
const QStringList C6UsersManager::getWhiteListUsers()
{
    QStringList nickList;
    
    for (unsigned int i=0; i < _whiteList.count(); i++)
    {
        C6Users *tmp = _whiteList.at(i);     
        nickList.append(tmp->getNick());       
    }           
   
    return(nickList);   
}


/*!
    \fn C6UsersManager::removeFromWhiteList(QString const & nick)
 */
void C6UsersManager::removeFromWhiteList(QString const & nick)
{
    for (unsigned int i=0; i < _whiteList.count(); i++)
    {
        C6Users *tmp = _whiteList.at(i);     
        if (tmp->getNick().compare(nick) == 0)
        {
            _whiteList.remove(i);
            break;        
        }                
    }     
}


/*!
    \fn C6UsersManager::isWhiteListed(QString const & nick)
 */
bool C6UsersManager::isWhiteListed(QString const & nick)
{
    bool found = false;

    for(int i=0; i < _whiteList.count(); i++)
    {
        C6Users *tmp = _whiteList.at(i);     
              
        if (tmp->getNick().compare(nick) == 0)
        {
            found =  true;
            break;
        }
    }
    
    return(found);
}
