Logo Search packages:      
Sourcecode: dc-qt version File versions  Download package

ClientNotifier.cpp

#include "ClientNotifier.h"
#include "SessionManager.h"

#include "RpcArgumentFactory.h"
#include "CommonTypes.h"
#include "log.h"
#include <iostream>
#include <boost/thread/recursive_mutex.hpp>
#include <boost/format.hpp>

using namespace rpc;

namespace dcqt_backend
{

ClientNotifier* ClientNotifier::inst = 0;

#define FOR_ALL_CLIENTS(c) driver->queueCommand( -1, c );

void ClientNotifier::connected(int aSessionId)
{
    //XmlRpcValue args,result;
    //args[0] = aSessionId;

    //FOR_ALL_CLIENTS(hubConnected);

    CmdPtr cmd(new list<boost::any>);

    cmd->push_back( string("hubConnected") );
    cmd->push_back( aSessionId );

    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::connectionFailed(int session,const string& reason)
{
    // XmlRpcValue args,result;
    //  args[0] = session;
    // args[1] = reason;
    //  FOR_ALL_CLIENTS(failed);
    CmdPtr cmd(new list<boost::any>);
    cmd->push_back( string("connectionFailed") );
    cmd->push_back( session );
    cmd->push_back( reason );

    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::hubUpdated(int aSessionId,const std::string& hubName)
{
    //   XmlRpcValue args,result;
    //  args[0] = aSessionId;
    //  args[1] = hubName;
    //  FOR_ALL_CLIENTS(hubUpdated);
    CmdPtr cmd(new list<boost::any>);
    cmd->push_back( string("hubUpdated") );
    cmd->push_back( aSessionId );
    cmd->push_back( hubName );
    FOR_ALL_CLIENTS( cmd );
}

void ClientNotifier::hubStats( int aSessionId, int64_t aAvailable )
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("hubStats") );
      cmd->push_back( aSessionId );
      cmd->push_back( aAvailable );
      FOR_ALL_CLIENTS( cmd );
}

void ClientNotifier::message(int aSessionId,const std::string& msg)
{
    //    XmlRpcValue args,result;
    //   args[0] = aSessionId;
    //   args[1] = msg.c_str();
    //   FOR_ALL_CLIENTS(chatMessage);
    CmdPtr cmd(new list<boost::any>);
    cmd->push_back( string("chatMessage") );
    cmd->push_back( aSessionId );
    cmd->push_back( msg );
    FOR_ALL_CLIENTS( cmd );
}

void ClientNotifier::userUpdated(int aSessionId,const ::User::Ptr& aUser)
{
    dcqt_backend::User& user = SessionManager::instance()->getUserPtrMap()[aUser];
    CmdPtr cmd(new list<boost::any>);
    cmd->push_back( string("userUpdated") );
    cmd->push_back( aSessionId );
    cmd->push_back( rpc_argument::createUser(user) );
    FOR_ALL_CLIENTS( cmd );
}

// void ClientNotifier::usersUpdated(int aSessionId, const ::User::List &ll)
// {
//     //    XmlRpcValue args,userlist,result;
//     //   int argi=0;
//     //    RpcArgumentFactory afac;
//     //   User::List::const_iterator it;
//     //   for (it = ll.begin (); it != ll.begin (); it++) {
//     //  if (!(*it)->isSet(User::HIDDEN)) {
//     //       backend::User& user = SessionManager::instance()->getUserPtrMap()[*it];
//     //       userlist[argi++] = afac.createUser(user);
//     //  }
//     //   }
//     //   args[0] = aSessionId;
//     //   args[1] = userlist;
//     //   FOR_ALL_CLIENTS(usersUpdated);
//     RpcDriver::CmdPtr cmd(new list<boost::any>);
//     RpcArgumentFactory afac;
//     list<boost::any> userlist;
//     int argi=0;
//     ::User::List::const_iterator it;
//     for (it = ll.begin (); it != ll.begin (); it++)
//     {
//         if (!(*it)->isSet(::User::HIDDEN))
//         {
//             dcqt_backend::User& user = SessionManager::instance()->getUserPtrMap()[*it];
//             userlist.push_back(afac.createUser(user));
//         }
//     }
//     cmd->push_back( string("usersUpdated"));
//     cmd->push_back( userlist );
//     FOR_ALL_CLIENTS(cmd);
// 
// 
// }


void ClientNotifier::usersUpdated(int sessionId, const vector<int>& updatedUsers)
{
    //  XmlRpcValue args,userlist,result;
      CmdPtr cmd(new list<boost::any>);
 
      cmd->push_back(string("usersUpdated"));
      cmd->push_back(sessionId);
      list<boost::any> userlist;
      
   for(int i=0;i < updatedUsers.size();i++) {
         if( SessionManager::instance()->getUserIdMap().find(updatedUsers[i]) == SessionManager::instance()->getUserIdMap().end() )
              continue;
         ::User::Ptr usr = SessionManager::instance()->getUserIdMap()[updatedUsers[i]];
         if (!usr->isSet(::User::HIDDEN)) {
             User& user = SessionManager::instance()->getUserPtrMap()[usr];
                userlist.push_back(rpc_argument::createUser(user));
            }
       }

      cmd->push_back( userlist );
      FOR_ALL_CLIENTS( cmd );
}

void ClientNotifier::userRemoved(int aSessionId,int aUserId)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("userRemoved") );
      cmd->push_back( aSessionId );
      cmd->push_back( aUserId );
      FOR_ALL_CLIENTS( cmd );
}

void ClientNotifier::hashInfo(string& file,int64_t bytesLeft,int filesLeft,int percentComplete)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("hashInfo"));
      cmd->push_back( file );
      cmd->push_back( bytesLeft );
      cmd->push_back( filesLeft );
      cmd->push_back( percentComplete );
      FOR_ALL_CLIENTS( cmd );
}


void ClientNotifier::searchResult(int aSessionId, SearchResult* res)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("searchResult") );
      cmd->push_back( aSessionId );

      cmd->push_back( rpc_argument::createSearchRes( res, SessionManager::instance()->getUserPtrMap()[res->getUser()].id ) );
    FOR_ALL_CLIENTS( cmd );
}

void ClientNotifier::searchResults(int aSessionId, vector<SearchResult*>& results)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("searchResults") );
      cmd->push_back( aSessionId );
      list<boost::any> srs;
      
    for(int i = 0;i < results.size();i++) {
       srs.push_back(rpc_argument::createSearchRes( results[i], SessionManager::instance()->getUserPtrMap()[results[i]->getUser()].id ));
    }
      cmd->push_back(srs);
    FOR_ALL_CLIENTS(cmd);
}


void ClientNotifier::getPassword(int aSessionId)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("passwordRequired") );
      cmd->push_back( aSessionId );
    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::privateMessage(int aSessionId,const ::User::Ptr& user,const std::string& msg)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("privateChatMessage") );
    
      cmd->push_back( aSessionId );
      cmd->push_back( user->getNick() );
      cmd->push_back( msg );
    FOR_ALL_CLIENTS(cmd);
}

00218 void ClientNotifier::transferEvent(TransferEvent e,Upload* u)
{
    //  XmlRpcValue args,result;
    CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("transferEvent") );

      cmd->push_back((int)e);
      cmd->push_back((int)UPLOAD);
      cmd->push_back( rpc_argument::createUpload(u));
    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::transferTick(const Upload::List& ul,TransferManager::UploadStatusMap& us)
{
    CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("transferEvent") );

    //     XmlRpcValue args,result;
      cmd->push_back((int)TICK);
      cmd->push_back((int)UPLOAD);
      list<boost::any> uploadList;
    Upload::List::const_iterator it;
    
    for(it=ul.begin();it!=ul.end();it++) {
      if(us[*it]==TransferManager::UPLOAD_STARTING)
          uploadList.push_back(rpc_argument::createUpload(*it));
    }
      cmd->push_back( uploadList );
    FOR_ALL_CLIENTS( cmd );
}

void ClientNotifier::transferEvent(TransferEvent e,Download* d)
{
      logger->info(boost::format("TransferEvent download"));
    CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("transferEvent") ); 
      cmd->push_back((int)e);
      cmd->push_back( (int) DOWNLOAD );
      cmd->push_back( rpc_argument::createDownload(d));

    FOR_ALL_CLIENTS(cmd);
}


void ClientNotifier::transferTick(const Download::List& ul)
{
      logger->info(boost::format("TransferTick download"));
    CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("transferEvent") ); 
      cmd->push_back( (int) TICK );
      cmd->push_back( (int) DOWNLOAD );
      list<boost::any> l;
    Download::List::const_iterator it;
    for(it=ul.begin();it!=ul.end();it++)
      l.push_back(rpc_argument::createDownload(*it));
    
      cmd->push_back( l );
    FOR_ALL_CLIENTS(cmd);
}


00279 void ClientNotifier::transferEvent(Upload* u,const string& error)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("transferEvent") );
      cmd->push_back( (int) FAILED );
      cmd->push_back( (int) UPLOAD );
    cmd->push_back( rpc_argument::createUpload(u) );
    cmd->push_back( error );
    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::transferEvent(Download* d,const string& error)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("transferEvent") );
      cmd->push_back( (int) FAILED );
      cmd->push_back( (int) DOWNLOAD );
    cmd->push_back( rpc_argument::createDownload(d) );
    cmd->push_back( error );
    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::queueEvent(QueueEvent event,QueueItem* item,int id)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("queueEvent") );

    QueueItem::Source::List::const_iterator iter;
    list<boost::any> sources;
      cmd->push_back((int)event);    
    switch(event) {
         case QUEUE_ADD:
                   cout << "QueueAdd" << endl;
             cmd->push_back(rpc_argument::createQueueItem(item,id));
             break;
         case QUEUE_REMOVE:
                   cout << "Queueremove" << endl;
             cmd->push_back(id);
             break;
         case QUEUE_FINISH:
                   cout << "Queuefinish" << endl;
             cmd->push_back(id);
             break;
         case QUEUE_SOURCE_UPDATE:
             {     
                   cout << "Queuesu" << endl;
                   cmd->push_back(id);
             iter = item->getSources().begin();
             //SessionManager::instance()->aquireLock();
                   boost::recursive_mutex::scoped_lock sl(SessionManager::instance()->sessionLock);
                   while( iter!=item->getSources().end()) {
                 sources.push_back(SessionManager::instance()->getUserPtrMap()[(*iter)->getUser()].id);
                 iter++;
             }
                   //SessionManager::instance()->releaseLock();
             cmd->push_back(sources);
             break;
             }     
         case QUEUE_STATUS_UPDATE:
                   cout << "Queuestatyup" << endl;
             cmd->push_back(id);
                   cmd->push_back((int)item->getStatus());
                   cmd->push_back((int)(item->getCurrent() ? (SessionManager::instance()->getUserPtrMap()[item->getCurrent()->getUser()].id) : (int)0));
             cmd->push_back((int)item->getPriority());
             break;
         default:
                   cout << "QueueHELVETE" << endl;
             return;
         }
    
         FOR_ALL_CLIENTS(cmd);
    
         // Check if this was a user file list download
         // in that case we need to parse the file list and send it to the client
      if ( QUEUE_FINISH == event  &&
             item->isSet( QueueItem::FLAG_USER_LIST ) &&
             TransferManager::getInstance()->isFileListRequested(SessionManager::instance()->getUserPtrMap()[item->getCurrent()->getUser()].id) ) {
                  CmdPtr cmd2(new list<boost::any>);
                        cmd2->push_back( string("userFileListing") );
                  // Store user id
                  cmd2->push_back(SessionManager::instance()->getUserPtrMap()[item->getCurrent()->getUser()].id);
                  // Parse the directory listing
                        cmd2->push_back( createFileListing( item ) );
                  // Notify clients
                  FOR_ALL_CLIENTS(cmd2);
    
                  // Remove the request from the transfermanager
                  TransferManager::getInstance()->removeFileListRequest(SessionManager::instance()->getUserPtrMap()[item->getCurrent()->getUser()].id );
      }
}


// Added
void ClientNotifier::finishedEvent(int type,int id,FinishedItem* item)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("finishedEvent") );
    cmd->push_back((int)FINISHED_EVENT_ADD);
    cmd->push_back(type);
    cmd->push_back(rpc_argument::createFinishedItem(item,id));
    FOR_ALL_CLIENTS(cmd);
}

// Removed
void ClientNotifier::finishedEvent(int type,int id)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("finishedEvent") );
    cmd->push_back((int)FINISHED_EVENT_REMOVE);
    cmd->push_back(type);
      cmd->push_back(id);
    FOR_ALL_CLIENTS(cmd);
}

// RemovedAll
void ClientNotifier::finishedEvent(int type)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("finishedEvent") );
    cmd->push_back((int)FINISHED_EVENT_REMOVEALL);
    cmd->push_back(type);
    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::newHubList()
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("newHubList") );
      cmd->push_back( rpc_argument::createHubList(SessionManager::instance()->getPublicHubs()) );
    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::favouriteHubAdded(const FavoriteHubEntry* e)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("favouriteHubAdded") );
    cmd->push_back(rpc_argument::createFavouriteHub(e));
    FOR_ALL_CLIENTS(cmd);
}

void ClientNotifier::favouriteHubRemoved(const string& server)
{
      CmdPtr cmd(new list<boost::any>);
      cmd->push_back( string("favouriteHubRemoved") );
    cmd->push_back(server);
    FOR_ALL_CLIENTS(cmd);
}

string ClientNotifier::createFileListing( QueueItem* item )
{
    std::string tree = "";
      try {
            // Create a new directory listing
            DirectoryListing listing( item->getCurrent()->getUser() );
            // Load the file from disk
            listing.loadFile( item->getListName() );
            
            
            // Add the user name as root
            tree += listing.getUser()->getNick();
            
            // Parse the nodes children
            parseDir( listing.getRoot(), tree, listing.getUtf8() );
            
            // Remove the last '*'
            tree = tree.substr( 0, tree.size() - 1 ); 
      }
      catch(...) {
            cerr << "Major fuck up" << endl;
      }

    return tree;
}

void ClientNotifier::parseDir( DirectoryListing::Directory::Ptr dir, std::string& tree, bool isUtf8 )
{

    // Check if the name is in UTF8
    tree += isUtf8 ? dir->getName() : Text::acpToUtf8( dir->getName() );

    std::sort( dir->directories.begin(), dir->directories.end(), DirectoryListing::Directory::DirSort() );

    // Add start of directory
    tree += "/";

    for ( DirectoryListing::Directory::Iter it = dir->directories.begin(); it != dir->directories.end(); it++)
    {

        parseDir( *it, tree, isUtf8 );
    }

    for ( DirectoryListing::File::Iter file = dir->files.begin(); file != dir->files.end(); file++ )
    {
        // Add file name and seperator
        tree += (*file)->getName() + "|";

        // Add size
            boost::format sizeFmter("%1%");
            sizeFmter % (*file)->getSize();
        tree += sizeFmter.str();

        // Add TTH
        tree += "|";
        tree += (*file)->getTTH() ? (*file)->getTTH()->toBase32() : "";

        // Add seperator between siblings
        tree += "*";
    }

    // Check if we added any directories or files. If so we remove the last '*'
    if ( dir->files.size() != 0 || dir->directories.size() != 0 )
    {
        tree = tree.substr( 0, tree.size() - 1 );
    }

    // Add end of directory
    tree += "\\*";
}
}

Generated by  Doxygen 1.6.0   Back to index