kontact

profilemanager.cpp
00001 /*
00002     This file is part of KDE Kontact.
00003 
00004     Copyright (c) 2007 Frank Osterfeld <frank.osterfeld@kdemail.net>
00005 
00006     This program is free software; you can redistribute it and/or modify
00007     it under the terms of the GNU General Public License as published by
00008     the Free Software Foundation; either version 2 of the License, or
00009     (at your option) any later version.
00010 
00011     This program is distributed in the hope that it will be useful,
00012     but WITHOUT ANY WARRANTY; without even the implied warranty of
00013     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
00014     GNU General Public License for more details.
00015 
00016     You should have received a copy of the GNU General Public License
00017     along with this program; if not, write to the Free Software
00018     Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00019 
00020     As a special exception, permission is given to link this program
00021     with any edition of TQt, and distribute the resulting executable,
00022     without including the source code for TQt in the source distribution.
00023 */
00024 
00025 #include "profilemanager.h"
00026 
00027 #include <tdeio/job.h>
00028 
00029 #include <tdeapplication.h>
00030 #include <tdeconfig.h>
00031 #include <tdeglobal.h>
00032 #include <kstandarddirs.h>
00033 #include <kstaticdeleter.h>
00034 #include <kurl.h>
00035 
00036 #include <tqdir.h>
00037 #include <tqstringlist.h>
00038 #include <tqvaluelist.h>
00039 
00040 Kontact::Profile::Profile( const TQString& id, bool isLocal ) : m_id( id ), m_local( isLocal )
00041 {
00042 }
00043 
00044 Kontact::Profile::Profile() : m_local( false )
00045 {
00046 }
00047 
00048 TQString Kontact::Profile::id() const
00049 {
00050     return m_id;
00051 }
00052 
00053 TQString Kontact::Profile::name() const
00054 {
00055     return m_name;
00056 }
00057 
00058 TQString Kontact::Profile::description() const
00059 {
00060     return m_description;
00061 }
00062 
00063 bool Kontact::Profile::isNull() const
00064 {
00065     return m_id.isNull();
00066 }
00067 
00068 void Kontact::Profile::setId( const TQString& id )
00069 {
00070     m_id = id;
00071 }
00072 
00073 void Kontact::Profile::setDescription( const TQString& description )
00074 {
00075     m_description = description;
00076 }
00077 
00078 void Kontact::Profile::setName( const TQString& name )
00079 {
00080     m_name = name;
00081 }
00082 
00083 void Kontact::Profile::setLocal( SetLocalMode mode )
00084 {
00085     if ( m_local )
00086         return;
00087 
00088     if ( mode == CopyProfileFiles )
00089         copyConfigFiles( m_originalLocation, localSaveLocation() );
00090 
00091     m_local = true;
00092 }
00093 
00094 bool Kontact::Profile::isLocal() const
00095 {
00096     return m_local;
00097 }
00098 
00099 void Kontact::Profile::setOriginalLocation( const TQString& path )
00100 {
00101     m_originalLocation = path;
00102 }
00103 
00104 TQString Kontact::Profile::localSaveLocation() const
00105 {
00106 
00107     return  m_id.isNull() ? TQString() : locateLocal( "data", "kontact/profiles/" + m_id, /*create folder=*/true );
00108 }
00109 
00110 TQString Kontact::Profile::saveLocation() const
00111 {
00112     return m_local ? localSaveLocation() : m_originalLocation;
00113 }
00114 
00115 bool Kontact::Profile::operator==( const Kontact::Profile& other ) const
00116 {
00117     return m_id == other.m_id && m_name == other.m_name && m_description == other.m_description;
00118 }
00119 
00120 Kontact::ProfileManager* Kontact::ProfileManager::m_self = 0;
00121 
00122 static KStaticDeleter<Kontact::ProfileManager> profileManagerSD;
00123 
00124 Kontact::ProfileManager* Kontact::ProfileManager::self() 
00125 {
00126     if ( m_self == 0 )
00127     {
00128         profileManagerSD.setObject( m_self, new Kontact::ProfileManager );
00129         m_self->readConfig();
00130     }
00131     return m_self;
00132 }
00133 
00134 Kontact::ProfileManager::ProfileManager( TQObject* parent ) : TQObject( parent )
00135 {
00136 }
00137 
00138 Kontact::ProfileManager::~ProfileManager()
00139 {
00140     writeConfig();
00141 }
00142 
00143 void Kontact::ProfileManager::writeConfig() const
00144 {
00145     const TQValueList<Kontact::Profile> profiles = m_profiles.values();
00146     for ( TQValueList<Kontact::Profile>::ConstIterator it = profiles.begin(), end = profiles.end(); it != end; ++it )
00147     {
00148         writeProfileConfig( *it );
00149     }
00150 }
00151 
00152 Kontact::Profile Kontact::ProfileManager::readFromConfiguration( const TQString& configFile, bool isLocal )
00153 {
00154     TDEConfig profileCfg( configFile, true /*read-only*/, false /*no KDE global*/ );
00155     const TQString configDir = configFile.left( configFile.findRev( TQDir::separator(), -1 ) );
00156     profileCfg.setGroup( "Kontact Profile" );
00157     const TQString id = profileCfg.readEntry( "Identifier" );
00158     Kontact::Profile profile( id );
00159     profile.setName( profileCfg.readEntry( "Name" ) );
00160     profile.setDescription( profileCfg.readEntry( "Description" ) );
00161     profile.setOriginalLocation( configDir );
00162     if ( isLocal )
00163         profile.setLocal( Kontact::Profile::DoNotCopyProfileFiles );
00164     return profile;
00165 }
00166 
00167 void Kontact::ProfileManager::writeProfileConfig( const Kontact::Profile& profile ) const
00168 {
00169     const TQString profileDir = profile.saveLocation();
00170     const TQString cfgPath = profileDir + "/profile.cfg";
00171     TDEConfig profileCfg( cfgPath, false /*read-only*/, false /*no KDE global*/ );
00172     profileCfg.setGroup( "Kontact Profile" );
00173     profileCfg.writeEntry( "Identifier", profile.id() );
00174     profileCfg.writeEntry( "Name", profile.name() );
00175     profileCfg.writeEntry( "Description", profile.description() );
00176 }
00177 
00178 void Kontact::ProfileManager::readConfig()
00179 {
00180     
00181     const TQStringList profilePaths = TDEGlobal::dirs()->findAllResources( "data", TQString::fromLatin1( "kontact/profiles/*/profile.cfg" ) );
00182 
00183     typedef TQMap<TQString, Kontact::Profile> ProfileMap;
00184     ProfileMap profiles;
00185     ProfileMap globalProfiles;
00186 
00187     const TQString localPrefix = locateLocal( "data", "kontact/profiles/", /*createDir=*/false );
00188     for ( TQStringList::ConstIterator it = profilePaths.begin(), end = profilePaths.end(); it != end; ++it )
00189     {
00190         const bool isLocal = (*it).startsWith( localPrefix );
00191         const Kontact::Profile profile = readFromConfiguration( *it, isLocal );
00192         if ( profile.isNull() )
00193             continue;
00194         if ( isLocal )
00195             profiles[profile.id()] = profile;
00196         else 
00197             globalProfiles[profile.id()] = profile;
00198     }
00199     
00200     for ( ProfileMap::ConstIterator it = globalProfiles.begin(), end = globalProfiles.end(); it != end; ++it )
00201     {
00202         if ( !profiles.contains( it.key() ) )
00203             profiles[it.key()] = it.data();
00204     }
00205 
00206     for ( ProfileMap::ConstIterator it = profiles.begin(), end = profiles.end(); it != end; ++it )
00207     {
00208         addProfile( *it, false /*dont sync config */ );
00209     }
00210 }
00211 
00212 TQValueList<Kontact::Profile> Kontact::ProfileManager::profiles() const
00213 {
00214     return m_profiles.values();
00215 }
00216 
00217 Kontact::Profile Kontact::ProfileManager::profileById( const TQString& id ) const
00218 {
00219     return m_profiles[id];
00220 }
00221 
00222 void Kontact::ProfileManager::updateProfile( const Kontact::Profile& profile_ )
00223 {
00224     const TQString id = profile_.id();
00225     if ( id.isNull() || m_profiles[id] == profile_ )
00226         return;
00227     Kontact::Profile profile( profile_ );
00228     m_profiles[id] = profile;
00229     profile.setLocal( Kontact::Profile::CopyProfileFiles );
00230     writeProfileConfig( profile );
00231     emit profileUpdated( id );
00232 }
00233 
00234 void Kontact::Profile::copyConfigFiles( const TQString& source_, const TQString& dest_ )
00235 {
00236     const KURL source = KURL::fromPathOrURL( source_+"/*rc" );
00237     const KURL dest = KURL::fromPathOrURL( dest_ );
00238     TDEIO::CopyJob* job = TDEIO::copy( source, dest, /*showProgressInfo=*/false );
00239     // TODO better check for the copy result
00240 }
00241 
00242 void Kontact::ProfileManager::saveToProfile( const TQString& id )
00243 {
00244     Kontact::Profile profile = profileById( id );
00245     if ( profile.isNull() )
00246         return;
00247     profile.setLocal( Kontact::Profile::CopyProfileFiles );
00248     writeProfileConfig( profile );
00249     emit saveToProfileRequested( id );
00250 }
00251 
00252 bool Kontact::ProfileManager::addProfile( const Kontact::Profile& profile, bool syncConfig )
00253 {
00254     const TQString id = profile.id();
00255     if ( m_profiles.contains( id ) )
00256         return false;
00257     m_profiles[id] = profile;
00258     emit profileAdded( id );
00259     emit saveToProfileRequested( id );
00260     if ( syncConfig ) {
00261         writeProfileConfig( profile );
00262     }
00263 
00264     return true;
00265 }
00266 
00267 void Kontact::ProfileManager::loadProfile( const TQString& id )
00268 {
00269     if ( !m_profiles.contains( id ) )
00270         return;
00271     emit profileLoaded( id );
00272 }
00273 
00274 void Kontact::ProfileManager::removeProfile( const Kontact::Profile& profile )
00275 {
00276     removeProfile( profile.id() );
00277 }
00278 
00279 void Kontact::ProfileManager::removeProfile( const TQString& id )
00280 {
00281     if ( !m_profiles.contains( id ) )
00282         return;
00283     Kontact::Profile profile = profileById( id );
00284     if ( profile.isLocal() ) {
00285         KURL location = KURL::fromPathOrURL( profile.saveLocation() );
00286         TDEIO::DeleteJob* job = TDEIO::del( location, /*shred*/ false, /*showProgressInfo=*/false );
00287         // TODO check result
00288     }
00289     m_profiles.remove( id );
00290     emit profileRemoved( id );
00291  }
00292 
00293 Kontact::ProfileManager::ExportError Kontact::ProfileManager::exportProfileToDirectory( const TQString& id, const TQString& path )
00294 {
00295     if ( !m_profiles.contains( id ) )
00296         return SuccessfulExport;
00297 
00298     if ( !TQDir( path ).exists() )
00299         return DirectoryDoesNotExist;
00300 
00301     const Kontact::Profile profile = profileById( id );
00302     const KURL source = KURL::fromPathOrURL( profile.saveLocation() );
00303     const KURL target = KURL::fromPathOrURL( path + TQDir::separator() + profile.name() );
00304 
00305     TDEIO::CopyJob* job = TDEIO::copy( source, target, /*showProgressInfo=*/false );
00306     // TODO check result
00307 
00308     return SuccessfulExport;
00309 }
00310 
00311 Kontact::ProfileManager::ImportError Kontact::ProfileManager::importProfileFromDirectory( const TQString& path )
00312 {
00313     Kontact::Profile profile = readFromConfiguration( path + "/profile.cfg", /*isLocal=*/ true );
00314     if ( profile.isNull() )
00315         return NoValidProfile;
00316 
00317     profile.setId( generateNewId() );
00318 
00319     const KURL source = KURL::fromPathOrURL( path );
00320     const KURL target = KURL::fromPathOrURL( profile.saveLocation() );
00321 
00322     TDEIO::CopyJob* job = TDEIO::copy( source, target, /*showProgressInfo=*/false );
00323     // TODO better check for the copy result
00324 
00325     addProfile( profile );
00326 
00327     return SuccessfulImport;
00328 }
00329 
00330 TQString Kontact::ProfileManager::generateNewId() const
00331 {
00332     while ( true )
00333     {
00334         const TQString newId = TDEApplication::randomString( 10 );
00335         if ( !m_profiles.contains( newId ) )
00336             return newId;
00337     }
00338 }
00339 
00340 #include "profilemanager.moc"