summaryrefslogtreecommitdiffstats
path: root/kpilot/conduits/docconduit/doc-conduit.cc
diff options
context:
space:
mode:
Diffstat (limited to 'kpilot/conduits/docconduit/doc-conduit.cc')
-rw-r--r--kpilot/conduits/docconduit/doc-conduit.cc1018
1 files changed, 0 insertions, 1018 deletions
diff --git a/kpilot/conduits/docconduit/doc-conduit.cc b/kpilot/conduits/docconduit/doc-conduit.cc
deleted file mode 100644
index fbaa22f59..000000000
--- a/kpilot/conduits/docconduit/doc-conduit.cc
+++ /dev/null
@@ -1,1018 +0,0 @@
-/* KPilot
-**
-** Copyright (C) 2002 by Reinhold Kainhofer
-**
-** The doc conduit synchronizes text files on the PC with DOC databases on the Palm
-*/
-
-/*
-** This program is free software; you can redistribute it and/or modify
-** it under the terms of the GNU General Public License as published by
-** the Free Software Foundation; either version 2 of the License, or
-** (at your option) any later version.
-**
-** This program is distributed in the hope that it will be useful,
-** but WITHOUT ANY WARRANTY; without even the implied warranty of
-** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-** GNU General Public License for more details.
-**
-** You should have received a copy of the GNU General Public License
-** along with this program in a file called COPYING; if not, write to
-** the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
-** MA 02110-1301, USA.
-*/
-
-/*
-** Bug reports and questions can be sent to kde-pim@kde.org.
-*/
-
-
-// naming of the bookmark file:
-// PDB->TXT: convert bookmarks to a .bm file
-// TXT->PDB: If a .bmk file exists, use it, otherwise use the .bm file (from the PDB->TXT conversion)
-// This way, the bookmark file is not overwritten, a manual bookmark file overrides, but the bookmarks from the handheld are still available
-
-
-#include "options.h"
-#include "doc-conduit.moc"
-
-#include <tqtimer.h>
-#include <tqdir.h>
-
-#include <kconfig.h>
-#include <kmdcodec.h>
-
-#include <pilotLocalDatabase.h>
-#include <pilotSerialDatabase.h>
-
-#include "doc-factory.h"
-#include "doc-conflictdialog.h"
-#include "DOC-converter.h"
-#include "pilotDOCHead.h"
-#include "docconduitSettings.h"
-
-
-// Something to allow us to check what revision
-// the modules are that make up a binary distribution.
-extern "C"
-{
-unsigned long version_conduit_doc = Pilot::PLUGIN_API;
-}
-
-TQString dirToString(eSyncDirectionEnum dir) {
- switch(dir) {
-// case eSyncAll: return "eSyncAll";
- case eSyncPDAToPC: return CSL1("eSyncPDAToPC");
- case eSyncPCToPDA: return CSL1("eSyncPCToPDA");
- case eSyncNone: return CSL1("eSyncNone");
- case eSyncConflict: return CSL1("eSyncConflict");
- case eSyncDelete: return CSL1("eSyncDelete");
- default: return CSL1("ERROR");
- }
-}
-
-
-/*********************************************************************
- C O N S T R U C T O R
- *********************************************************************/
-
-
-DOCConduit::DOCConduit(KPilotLink * o,
- const char *n, const TQStringList & a):ConduitAction(o, n, a)
-{
- FUNCTIONSETUP;
- fConduitName=i18n("DOC");
-}
-
-
-
-DOCConduit::~DOCConduit()
-{
- FUNCTIONSETUP;
-}
-
-
-bool DOCConduit::isCorrectDBTypeCreator(DBInfo dbinfo) {
- return dbinfo.type == dbtype() && dbinfo.creator == dbcreator();
-}
-const unsigned long DOCConduit::dbtype() {
- return get_long(DOCConduitFactory::dbDOCtype);
-}
-const unsigned long DOCConduit::dbcreator() {
- return get_long(DOCConduitFactory::dbDOCcreator);
-}
-
-
-
-/*********************************************************************
- L O A D I N G T H E D A T A
- *********************************************************************/
-
-
-
-void DOCConduit::readConfig()
-{
- FUNCTIONSETUP;
- DOCConduitSettings::self()->readConfig();
-
- eConflictResolution = (enum eSyncDirectionEnum) (DOCConduitSettings::conflictResolution() );
- fTXTBookmarks = DOCConverter::eBmkNone;
- if ( DOCConduitSettings::convertBookmarks() )
- {
- if ( DOCConduitSettings::bmkFileBookmarks() )
- fTXTBookmarks |= DOCConverter::eBmkFile;
- if ( DOCConduitSettings::inlineBookmarks() )
- fTXTBookmarks |= DOCConverter::eBmkInline;
- if ( DOCConduitSettings::endtagBookmarks() )
- fTXTBookmarks |= DOCConverter::eBmkEndtags;
- }
-
- eSyncDirection = (enum eSyncDirectionEnum)(DOCConduitSettings::syncDirection() );
-
-#ifdef DEBUG
- DEBUGKPILOT << fname
- << ": Settings "
- << " tXTDirectory=" << DOCConduitSettings::tXTDirectory()
- << " pDBDirectory=" << DOCConduitSettings::pDBDirectory()
- << " keepPDBLocally=" << DOCConduitSettings::keepPDBsLocally()
- << " eConflictResolution=" << eConflictResolution
- << " tXTBookmarks=" << fTXTBookmarks
- << " pDBBookmarks=" << DOCConduitSettings::bookmarksToPC()
- << " compress=" << DOCConduitSettings::compress()
- << " eSyncDirection=" << eSyncDirection << endl;
-#endif
-}
-
-
-
-bool DOCConduit::pcTextChanged(TQString txtfn)
-{
- FUNCTIONSETUP;
- // How do I find out if a text file has changed shince we last synced it??
- // Use KMD5 for now. If I realize it is too slow, then I have to go back to comparing modification times
- // if there is no config setting yet, assume the file has been changed. the md5 sum will be written to the config file after the sync.
- TQString oldDigest=DOCConduitSettings::self()->config()->readEntry(txtfn);
- if (oldDigest.length()<=0)
- {
- return true;
- }
-#ifdef DEBUG
- DEBUGKPILOT<<"Old digest is "<<oldDigest<<endl;
-#endif
-
- KMD5 docmd5;
- TQFile txtfile(txtfn);
- if (txtfile.open(IO_ReadOnly)){
- docmd5.update(txtfile);
- TQString thisDigest(docmd5.hexDigest() /* .data() */);
-#ifdef DEBUG
- DEBUGKPILOT<<"New digest is "<<thisDigest<<endl;
-#endif
- return (thisDigest.length()<=0) || (thisDigest!=oldDigest);
- } else {
- // File does not exist. This should actually never happen. Anyways, just return true to indicate it has changed.
- // doSync should detect this and delete the doc from the handheld.
- return true;
- }
- return false;
-}
-
-
-
-bool DOCConduit::hhTextChanged(PilotDatabase*docdb)
-{
- FUNCTIONSETUP;
- if (!docdb) return false;
-
- PilotRecord *firstRec = docdb->readRecordByIndex(0);
- PilotDOCHead docHeader(firstRec);
- KPILOT_DELETE(firstRec);
-
- int storyRecs = docHeader.numRecords;
-
- // determine the index of the next modified record (does it lie
- // beyond the actual text records?)
- int modRecInd=-1;
- PilotRecord*modRec=docdb->readNextModifiedRec(&modRecInd);
-#ifdef DEBUG
- DEBUGKPILOT<<"Index of first changed record: "<<modRecInd<<endl;
-#endif
-
- KPILOT_DELETE(modRec);
- // if the header record was changed, find out which is the first changed
- // real document record:
- if (modRecInd==0) {
- modRec=docdb->readNextModifiedRec(&modRecInd);
-#ifdef DEBUG
- DEBUGKPILOT<<"Reread Index of first changed records: "<<modRecInd<<endl;
-#endif
- KPILOT_DELETE(modRec);
- }
-
- // The record index starts with 0, so only a negative number means
- // no modified record was found
- if (modRecInd >= 0) {
-#ifdef DEBUG
- DEBUGKPILOT<<"Handheld side has changed, condition="<<
- ((!DOCConduitSettings::ignoreBmkChanges()) || (modRecInd <= storyRecs))<<endl;
-#endif
- if ((!DOCConduitSettings::ignoreBmkChanges()) || (modRecInd <= storyRecs))
- return true;
- } else {
-#ifdef DEBUG
- DEBUGKPILOT<<"Handheld side has NOT changed!"<<endl;
-#endif
- return false;
- }
- return false;
-}
-
-
-
-/*********************************************************************
- * Helper functions
- ********************************************************************/
-
-TQString DOCConduit::constructPDBFileName(TQString name) {
- FUNCTIONSETUP;
- TQString fn;
- TQDir dr(DOCConduitSettings::pDBDirectory());
- TQFileInfo pth(dr, name);
- if (!name.isEmpty()) fn=pth.absFilePath()+CSL1(".pdb");
- return fn;
-}
-TQString DOCConduit::constructTXTFileName(TQString name) {
- FUNCTIONSETUP;
- TQString fn;
- TQDir dr( DOCConduitSettings::tXTDirectory() );
- TQFileInfo pth(dr, name);
- if (!name.isEmpty()) fn=pth.absFilePath()+CSL1(".txt");
- return fn;
-}
-
-
-
-
-
-/*********************************************************************
- S Y N C S T R U C T U R E
- *********************************************************************/
-
-
-
-
-
-/* virtual */ bool DOCConduit::exec()
-{
- FUNCTIONSETUP;
-
- readConfig();
- dbnr=0;
-
- emit logMessage(i18n("Searching for texts and databases to synchronize"));
-
- TQTimer::singleShot(0, this, TQT_SLOT(syncNextDB()));
- return true;
-}
-
-
-
-bool DOCConduit::doSync(docSyncInfo &sinfo)
-{
- FUNCTIONSETUP;
- bool res=false;
-
- if (sinfo.direction==eSyncDelete) {
- if (!sinfo.txtfilename.isEmpty()) {
- if (!TQFile::remove(sinfo.txtfilename)) {
- WARNINGKPILOT << "Unable to delete the text file " << sinfo.txtfilename << " on the PC" << endl;
- }
- TQString bmkfilename = sinfo.txtfilename;
- if (bmkfilename.endsWith(CSL1(".txt"))){
- bmkfilename.remove(bmkfilename.length()-4, 4);
- }
- bmkfilename+=CSL1(PDBBMK_SUFFIX);
- if (!TQFile::remove(bmkfilename)) {
-#ifdef DEBUG
- DEBUGKPILOT<<"Could not remove bookmarks file "<<bmkfilename<<" for database "<<sinfo.handheldDB<<endl;
-#endif
- }
- }
- if (!sinfo.pdbfilename.isEmpty() && DOCConduitSettings::keepPDBsLocally() ) {
- PilotLocalDatabase*database=new PilotLocalDatabase(DOCConduitSettings::pDBDirectory(),
- TQString::fromLatin1(sinfo.dbinfo.name), false);
- if (database) {
- if ( database->deleteDatabase() !=0 ) {
- WARNINGKPILOT << "Unable to delete database " << sinfo.dbinfo.name << " on the PC" << endl;
- }
- KPILOT_DELETE(database);
- }
- }
- if (!DOCConduitSettings::localSync()) {
- PilotDatabase *database=deviceLink()->database( sinfo.dbinfo.name );
- if ( database->deleteDatabase() !=0 ) {
- WARNINGKPILOT << "Unable to delete database " << sinfo.dbinfo.name << " from the handheld" << endl;
- }
- KPILOT_DELETE(database);
- }
- return true;
- }
- // preSyncAction should initialize the custom databases/files for the
- // specific action chosen for this db and return a pointer to a docDBInfo
- // instance which points either to a local database or a database on the handheld.
- PilotDatabase *database = preSyncAction(sinfo);
-
- if (database && ( !database->isOpen() ) ) {
-#ifdef DEBUG
- DEBUGKPILOT<<"Database "<<sinfo.dbinfo.name<<" does not yet exist. Creating it:"<<endl;
-#endif
- if (!database->createDatabase(dbcreator(), dbtype()) ) {
-#ifdef DEBUG
- DEBUGKPILOT<<"Failed"<<endl;
- emit logMessage(i18n("Database created."));
-#endif
- }
- }
-
- if (database && database->isOpen()) {
- DOCConverter docconverter;
- connect(&docconverter, TQT_SIGNAL(logError(const TQString &)), TQT_SIGNAL(logError(const TQString &)));
- connect(&docconverter, TQT_SIGNAL(logMessage(const TQString &)), TQT_SIGNAL(logMessage(const TQString &)));
-
- docconverter.setTXTpath( DOCConduitSettings::tXTDirectory(), sinfo.txtfilename );
- docconverter.setPDB(database);
- docconverter.setCompress(DOCConduitSettings::compress());
-
- switch (sinfo.direction) {
- case eSyncPDAToPC:
- docconverter.setBookmarkTypes(DOCConduitSettings::bookmarksToPC());
- res = docconverter.convertPDBtoTXT();
- break;
- case eSyncPCToPDA:
- docconverter.setBookmarkTypes(fTXTBookmarks);
- res = docconverter.convertTXTtoPDB();
- break;
- default:
- break;
- }
-
- // Now calculate the md5 checksum of the PC text and write it to the config file
- if (res)
- {
- KMD5 docmd5;
- TQFile txtfile(docconverter.txtFilename());
- if (txtfile.open(IO_ReadOnly)) {
- docmd5.update(txtfile);
- TQString thisDigest(docmd5.hexDigest() /* .data() */);
- DOCConduitSettings::self()->config()->writeEntry(docconverter.txtFilename(), thisDigest);
- DOCConduitSettings::self()->config()->sync();
-#ifdef DEBUG
- DEBUGKPILOT<<"MD5 Checksum of the text "<<sinfo.txtfilename<<" is "<<thisDigest<<endl;
-#endif
- } else {
-#ifdef DEBUG
- DEBUGKPILOT<<"couldn't open file "<<docconverter.txtFilename()<<" for reading!!!"<<endl;
-#endif
- }
- }
-
- if (!postSyncAction(database, sinfo, res))
- emit logError(i18n("Unable to install the locally created PalmDOC %1 to the handheld.")
- .arg(TQString::fromLatin1(sinfo.dbinfo.name)));
- if (!res)
- emit logError(i18n("Conversion of PalmDOC \"%1\" failed.")
- .arg(TQString::fromLatin1(sinfo.dbinfo.name)));
-// disconnect(&docconverter, TQT_SIGNAL(logError(const TQString &)), TQT_SIGNAL(logError(const TQString &)));
-// disconnect(&docconverter, TQT_SIGNAL(logMessage(const TQString &)), TQT_SIGNAL(logMessage(const TQString &)));
-// KPILOT_DELETE(database);
- }
- else
- {
- emit logError(i18n("Unable to open or create the database %1.")
- .arg(TQString::fromLatin1(sinfo.dbinfo.name)));
- }
- return res;
-}
-
-
-/** syncNextDB walks through all PalmDoc databases on the handheld and decides if they are supposed to be synced to the PC.
- * syncNextDB and syncNextTXT fist build the list of all PalmDoc texts, and then the method syncDatabases does the actual sync. */
-void DOCConduit::syncNextDB() {
- FUNCTIONSETUP;
- DBInfo dbinfo;
-
- if (eSyncDirection==eSyncPCToPDA || fHandle->findDatabase(NULL, &dbinfo, dbnr, dbtype(), dbcreator() /*, cardno */ ) < 0)
- {
- // no more databases available, so check for PC->Palm sync
- TQTimer::singleShot(0, this, TQT_SLOT(syncNextTXT()));
- return;
- }
- dbnr=dbinfo.index+1;
-#ifdef DEBUG
- DEBUGKPILOT<<"Next Palm database to sync: "<<dbinfo.name<<", Index="<<dbinfo.index<<endl;
-#endif
-
- // if creator and/or type don't match, go to next db
- if (!isCorrectDBTypeCreator(dbinfo) ||
- fDBNames.contains(TQString::fromLatin1(dbinfo.name)))
- {
- TQTimer::singleShot(0, this, TQT_SLOT(syncNextDB()));
- return;
- }
-
- TQString txtfilename=constructTXTFileName(TQString::fromLatin1(dbinfo.name));
- TQString pdbfilename=constructPDBFileName(TQString::fromLatin1(dbinfo.name));
-
- docSyncInfo syncInfo(TQString::fromLatin1(dbinfo.name),
- txtfilename, pdbfilename, eSyncNone);
- syncInfo.dbinfo=dbinfo;
- needsSync(syncInfo);
- fSyncInfoList.append(syncInfo);
- fDBNames.append(TQString::fromLatin1(dbinfo.name));
-
- TQTimer::singleShot(0, this, TQT_SLOT(syncNextDB()));
- return;
-}
-
-
-
-void DOCConduit::syncNextTXT()
-{
- FUNCTIONSETUP;
-
- if (eSyncDirection==eSyncPDAToPC )
- {
- // We don't sync from PC to PDB, so start the conflict resolution and then the actual sync process
- docnames.clear();
- TQTimer::singleShot(0, this, TQT_SLOT(checkPDBFiles()));
- return;
- }
-
- // if docnames isn't initialized, get a list of all *.txt files in DOCConduitSettings::tXTDirectory()
- if (docnames.isEmpty()/* || dociterator==docnames.end() */) {
- docnames=TQDir( DOCConduitSettings::tXTDirectory(), CSL1("*.txt")).entryList() ;
- dociterator=docnames.begin();
- }
- if (dociterator==docnames.end()) {
- // no more databases available, so start the conflict resolution and then the actual sync proces
- docnames.clear();
- TQTimer::singleShot(0, this, TQT_SLOT(checkPDBFiles()));
- return;
- }
-
- TQString fn=(*dociterator);
-
- TQDir dr( DOCConduitSettings::tXTDirectory() );
- TQFileInfo fl(dr, fn );
- TQString txtfilename=fl.absFilePath();
- TQString pdbfilename;
- ++dociterator;
-
- DBInfo dbinfo;
- // Include all "extensions" except the last. This allows full stops inside the database name (e.g. abbreviations)
- // first fill everything with 0, so we won't have a buffer overflow.
- memset(&dbinfo.name[0], 0, 33);
- strncpy(&dbinfo.name[0], fl.baseName(TRUE).latin1(), 30);
-
- bool alreadySynced=fDBNames.contains(fl.baseName(TRUE));
- if (!alreadySynced) {
- docSyncInfo syncInfo(TQString::fromLatin1(dbinfo.name),
- txtfilename, pdbfilename, eSyncNone);
- syncInfo.dbinfo=dbinfo;
- needsSync(syncInfo);
- fSyncInfoList.append(syncInfo);
- fDBNames.append(TQString::fromLatin1(dbinfo.name));
- } else {
-#ifdef DEBUG
- DEBUGKPILOT<<txtfilename<<" has already been synced, skipping it."<<endl;
-#endif
- }
-
- TQTimer::singleShot(0, this, TQT_SLOT(syncNextTXT()));
- return;
-}
-
-
-
-/** This slot will only be used if DOCConduitSettings::keepPDBsLocally() to check if new doc databases have been copied to the pdb directory.
- * If so, install it to the handheld and sync it to the PC */
-void DOCConduit::checkPDBFiles() {
- FUNCTIONSETUP;
-
- if ( DOCConduitSettings::localSync() || !DOCConduitSettings::keepPDBsLocally() || eSyncDirection==eSyncPCToPDA )
- {
- // no more databases available, so check for PC->Palm sync
- TQTimer::singleShot(0, this, TQT_SLOT(checkDeletedDocs()));
- return;
- }
-
- // Walk through all files in the pdb directory and check if it has already been synced.
- // if docnames isn't initialized, get a list of all *.pdb files in DOCConduitSettings::pDBDirectory()
- if (docnames.isEmpty()/* || dociterator==docnames.end() */) {
- docnames=TQDir(DOCConduitSettings::pDBDirectory(), CSL1("*.pdb")).entryList() ;
- dociterator=docnames.begin();
- }
- if (dociterator==docnames.end()) {
- // no more databases available, so start the conflict resolution and then the actual sync proces
- docnames.clear();
- TQTimer::singleShot(0, this, TQT_SLOT(checkDeletedDocs()));
- return;
- }
-
- TQString fn=(*dociterator);
-
- TQDir dr(DOCConduitSettings::pDBDirectory());
- TQFileInfo fl(dr, fn );
- TQString pdbfilename=fl.absFilePath();
- ++dociterator;
-
- // Get the doc title and check if it has already been synced (in the synced docs list of in fDBNames to be synced)
- // If the doc title doesn't appear in either list, install it to the Handheld, and add it to the list of dbs to be synced.
- TQString dbname=fl.baseName(TRUE).left(30);
- if (!fDBNames.contains(dbname) && !fDBListSynced.contains(dbname)) {
- if (fHandle->installFiles(pdbfilename, false)) {
- DBInfo dbinfo;
- // Include all "extensions" except the last. This allows full stops inside the database name (e.g. abbreviations)
- // first fill everything with 0, so we won't have a buffer overflow.
- memset(&dbinfo.name[0], 0, 33);
- strncpy(&dbinfo.name[0], dbname.latin1(), 30);
-
- docSyncInfo syncInfo(dbname, constructTXTFileName(dbname), pdbfilename, eSyncNone);
- syncInfo.dbinfo=dbinfo;
- needsSync(syncInfo);
- fSyncInfoList.append(syncInfo);
- fDBNames.append(dbname);
- } else {
-#ifdef DEBUG
- DEBUGKPILOT<<"Could not install database "<<dbname<<" ("<<pdbfilename<<") to the handheld"<<endl;
-#endif
- }
- }
-
- TQTimer::singleShot(0, this, TQT_SLOT(checkPDBFiles()));
-}
-
-
-
-void DOCConduit::checkDeletedDocs()
-{
- FUNCTIONSETUP;
-
- for (TQStringList::Iterator it=fDBListSynced.begin(); it!=fDBListSynced.end(); ++it ) {
- if (!fDBNames.contains(*it)) {
- // We need to delete this doc:
- TQString dbname(*it);
- TQString txtfilename=constructTXTFileName(dbname);
- TQString pdbfilename=constructPDBFileName(dbname);
- docSyncInfo syncInfo(dbname, txtfilename, pdbfilename, eSyncDelete);
-
- DBInfo dbinfo;
- memset(&dbinfo.name[0], 0, 33);
- strncpy(&dbinfo.name[0], dbname.latin1(), 30);
- syncInfo.dbinfo=dbinfo;
-
- fSyncInfoList.append(syncInfo);
- }
- }
- TQTimer::singleShot(0, this, TQT_SLOT(resolve()));
- return;
-}
-
-
-
-void DOCConduit::resolve() {
- FUNCTIONSETUP;
-
- for (fSyncInfoListIterator=fSyncInfoList.begin(); fSyncInfoListIterator!=fSyncInfoList.end(); ++fSyncInfoListIterator) {
- // Walk through each database and apply the conflictResolution option.
- // the remaining conflicts will be resolved in the resolution dialog
- if ((*fSyncInfoListIterator).direction==eSyncConflict){
-#ifdef DEBUG
- DEBUGKPILOT<<"We have a conflict for "<<(*fSyncInfoListIterator).handheldDB<<", default="<<eConflictResolution<<endl;
-#endif
- switch (eConflictResolution)
- {
- case eSyncPDAToPC:
-#ifdef DEBUG
- DEBUGKPILOT<<"PDA overrides for database "<<(*fSyncInfoListIterator).handheldDB<<endl;
-#endif
- (*fSyncInfoListIterator).direction = eSyncPDAToPC;
- break;
- case eSyncPCToPDA:
-#ifdef DEBUG
- DEBUGKPILOT<<"PC overrides for database "<<(*fSyncInfoListIterator).handheldDB<<endl;
-#endif
- (*fSyncInfoListIterator).direction = eSyncPCToPDA;
- break;
- case eSyncNone:
-#ifdef DEBUG
- DEBUGKPILOT<<"No sync for database "<<(*fSyncInfoListIterator).handheldDB<<endl;
-#endif
- (*fSyncInfoListIterator).direction = eSyncNone;
- break;
- case eSyncDelete:
- case eSyncConflict:
- default:
-#ifdef DEBUG
- DEBUGKPILOT<<"Conflict remains due to default resolution setting for database "<<(*fSyncInfoListIterator).handheldDB<<endl;
-#endif
- break;
- }
- }
- }
-
- // Show the conflict resolution dialog and ask for the action for each database
- ResolutionDialog*dlg=new ResolutionDialog( 0, i18n("Conflict Resolution"), &fSyncInfoList , fHandle);
- bool show=DOCConduitSettings::alwaysShowResolutionDialog() || (dlg && dlg->hasConflicts);
- if (show) {
- if (!dlg || !dlg->exec() ) {
- KPILOT_DELETE(dlg)
- emit logMessage(i18n("Sync aborted by user."));
- TQTimer::singleShot(0, this, TQT_SLOT(cleanup()));
- return;
- }
- }
- KPILOT_DELETE(dlg)
-
-
- // fDBNames will be filled with the names of the databases that are actually synced (not deleted), so I can write the list to the config file
- fDBNames.clear();
- fSyncInfoListIterator=fSyncInfoList.begin();
- TQTimer::singleShot(0,this, TQT_SLOT(syncDatabases()));
- return;
-}
-
-
-
-void DOCConduit::syncDatabases() {
- FUNCTIONSETUP;
- if (fSyncInfoListIterator==fSyncInfoList.end()) {
- // We're done, so clean up
- TQTimer::singleShot(0, this, TQT_SLOT(cleanup()));
- return;
- }
-
- docSyncInfo sinfo=(*fSyncInfoListIterator);
- ++fSyncInfoListIterator;
-
- switch (sinfo.direction) {
- case eSyncConflict:
-#ifdef DEBUG
- DEBUGKPILOT<<"Entry "<<sinfo.handheldDB<<"( txtfilename: "<<sinfo.txtfilename<<
- ", pdbfilename: "<<sinfo.pdbfilename<<") had sync direction eSyncConflict!!!"<<endl;
-#endif
- break;
- case eSyncDelete:
- case eSyncPDAToPC:
- case eSyncPCToPDA:
- emit logMessage(i18n("Synchronizing text \"%1\"").arg(sinfo.handheldDB));
- if (!doSync(sinfo)) {
- // The sync could not be done, so inform the user (the error message should probably issued inside doSync)
-#ifdef DEBUG
- DEBUGKPILOT<<"There was some error syncing the text \""<<sinfo.handheldDB<<"\" with the file "<<sinfo.txtfilename<<endl;
-#endif
- }
- break;
- case eSyncNone:
-// case eSyncAll:
- break;
- }
- if (sinfo.direction != eSyncDelete) fDBNames.append(sinfo.handheldDB);
-
- TQTimer::singleShot(0,this, TQT_SLOT(syncDatabases()));
- return;
-}
-
-
-PilotDatabase*DOCConduit::openDOCDatabase(const TQString &dbname) {
- if (DOCConduitSettings::localSync())
- {
- return new PilotLocalDatabase(DOCConduitSettings::pDBDirectory(), dbname, false);
- }
- else
- {
- return deviceLink()->database( dbname );
- }
-}
-
-
-bool DOCConduit::needsSync(docSyncInfo &sinfo)
-{
- FUNCTIONSETUP;
- sinfo.direction = eSyncNone;
-
- PilotDatabase*docdb=openDOCDatabase(TQString::fromLatin1(sinfo.dbinfo.name));
- if (!fDBListSynced.contains(sinfo.handheldDB)) {
- // the database wasn't included on last sync, so it has to be new.
-#ifdef DEBUG
- DEBUGKPILOT<<"Database "<<sinfo.dbinfo.name<<" wasn't included in the previous sync!"<<endl;
-#endif
-
- /* Resolution Table:
- PC HH | normal PC->HH HH->PC
- -----------------------------------------
- N - | P P D
- - N | H D H
- N N | C P H
- */
-
- if (TQFile::exists(sinfo.txtfilename)) sinfo.fPCStatus=eStatNew;
- else sinfo.fPCStatus=eStatDoesntExist;
- if (docdb && docdb->isOpen()) sinfo.fPalmStatus=eStatNew;
- else sinfo.fPalmStatus=eStatDoesntExist;
- KPILOT_DELETE(docdb);
-
- switch (eSyncDirection) {
- case eSyncPDAToPC:
- if (sinfo.fPalmStatus==eStatDoesntExist)
- sinfo.direction=eSyncDelete;
- else sinfo.direction=eSyncPDAToPC;
- break;
- case eSyncPCToPDA:
- if (sinfo.fPCStatus==eStatDoesntExist)
- sinfo.direction=eSyncDelete;
- else sinfo.direction=eSyncPCToPDA;
- break;
- case eSyncNone: // means actually both directions!
- if (sinfo.fPCStatus==eStatNew) {
- if (sinfo.fPalmStatus==eStatNew) sinfo.direction=eSyncConflict;
- else sinfo.direction=eSyncPCToPDA;
- } else {
- if (sinfo.fPalmStatus==eStatNew) sinfo.direction=eSyncPDAToPC;
- else {
- sinfo.direction=eSyncNone;
-#ifdef DEBUG
- DEBUGKPILOT<<"I'm supposed to find a sync direction, but the "<<
- " text "<<sinfo.dbinfo.name<<" doesn't exist on either "<<
- " the handheld or the PC"<<endl;
-#endif
- }
- }
- break;
- default:
- break;
- }
- return true;
- }
-
- // Text was included in the last sync
- if (!TQFile::exists(sinfo.txtfilename)) sinfo.fPCStatus=eStatDeleted;
- else if(pcTextChanged(sinfo.txtfilename)) {
- sinfo.fPCStatus=eStatChanged;
-#ifdef DEBUG
- DEBUGKPILOT<<"PC side has changed!"<<endl;
-#endif
- // TODO: Check for changed bookmarks on the PC side
-#ifdef DEBUG
- } else {
- DEBUGKPILOT<<"PC side has NOT changed!"<<endl;
-#endif
- }
-
- if (!docdb || !docdb->isOpen()) sinfo.fPalmStatus=eStatDeleted;
- else if (hhTextChanged(docdb)) {
-#ifdef DEBUG
- DEBUGKPILOT<<"Handheld side has changed!"<<endl;
-#endif
- sinfo.fPalmStatus=eStatChanged;
-#ifdef DEBUG
- } else {
- DEBUGKPILOT<<"Handheld side has NOT changed!"<<endl;
-#endif
- }
- KPILOT_DELETE(docdb);
-
-
- // Now that we know the status of both sides, determine what to do.
- /* Resolution Table:
- PC HH | normal PC->HH HH->PC
- -----------------------------------------
- - - | - - -
- C - | P P H
- - C | H P H
- C C | C P H
- D - | D D H
- - D | D P D
- D D | D D D
- -----------------------------------------
- C D | C P D
- D C | C D H
- */
-
-
- if (sinfo.fPCStatus == eStatNone && sinfo.fPalmStatus==eStatNone) {
-#ifdef DEBUG
- DEBUGKPILOT<<"Nothing has changed, not need for a sync."<<endl;
-#endif
- sinfo.direction=eSyncNone;
- return false;
- }
-
- // In all other cases, if only one direction (PC->HH or HH->PC)
- // should be done, check if the DB was deleted or if we are supposed
- // to sync that direction
-
- if (eSyncDirection==eSyncPCToPDA) {
- if (sinfo.fPCStatus==eStatDeleted) sinfo.direction=eSyncDelete;
- else sinfo.direction=eSyncPCToPDA;
- return true;
- }
- if (eSyncDirection==eSyncPDAToPC) {
- if (sinfo.fPalmStatus==eStatDeleted) sinfo.direction=eSyncDelete;
- else sinfo.direction=eSyncPDAToPC;
- return true;
- }
-
-
- // ---------------------------------------------------------------
- // Finally, do the normal case, where both directions are possible
- // ---------------------------------------------------------------
-
-
- // if either is deleted, and the other is not changed, delete
- if ( ((sinfo.fPCStatus==eStatDeleted) && (sinfo.fPalmStatus!=eStatChanged)) ||
- ((sinfo.fPalmStatus==eStatDeleted) && (sinfo.fPCStatus!=eStatChanged)) )
- {
-#ifdef DEBUG
- DEBUGKPILOT<<"DB was deleted on one side and not changed on "
- "the other -> Delete it."<<endl;
-#endif
- sinfo.direction=eSyncDelete;
- return true;
- }
-
- // eStatDeleted (and both not changed) have already been treated, for all
- // other values in combination with eStatNone, just copy the texts.
- if (sinfo.fPCStatus==eStatNone) {
-#ifdef DEBUG
- DEBUGKPILOT<<"PC side has changed!"<<endl;
-#endif
- sinfo.direction=eSyncPDAToPC;
- return true;
- }
-
- if (sinfo.fPalmStatus==eStatNone) {
- sinfo.direction=eSyncPCToPDA;
- return true;
- }
-
- // All other cases
- // (deleted,changed), (changed, deleted), (changed,changed)
- // create a conflict:
- sinfo.direction=eSyncConflict;
- return true;
-}
-
-
-
-PilotDatabase *DOCConduit::preSyncAction(docSyncInfo &sinfo) const
-{
- FUNCTIONSETUP;
-
- {
- // make sure the dir for the local texts really exists!
- TQDir dir( DOCConduitSettings::tXTDirectory() );
- if (!dir.exists())
- {
- dir.mkdir(dir.absPath());
- }
- }
-
- DBInfo dbinfo=sinfo.dbinfo;
- switch (sinfo.direction)
- {
- case eSyncPDAToPC:
- if (DOCConduitSettings::keepPDBsLocally())
- {
- // make sure the dir for the local db really exists!
- TQDir dir(DOCConduitSettings::pDBDirectory());
-
- if (!dir.exists())
- {
- dir.mkdir(dir.absPath());
- }
-#ifdef DEBUG
- DEBUGKPILOT<<"Need to fetch database "<<dbinfo.name<<
- " to the directory "<<dir.absPath()<<endl;
-#endif
- dbinfo.flags &= ~dlpDBFlagOpen;
-
- if (!fHandle->retrieveDatabase(sinfo.pdbfilename, &dbinfo) )
- {
- WARNINGKPILOT << "Unable to retrieve database " << dbinfo.name <<
- " from the handheld into " << sinfo.pdbfilename << "." << endl;
- return 0L;
- }
- }
- break;
- case eSyncPCToPDA:
- if (DOCConduitSettings::keepPDBsLocally())
- {
- // make sure the dir for the local db really exists!
- TQDir dir(DOCConduitSettings::pDBDirectory());
- if (!dir.exists())
- {
- dir.mkdir(dir.absPath());
- }
- }
- break;
- default:
- break;
- }
- if (DOCConduitSettings::keepPDBsLocally())
- {
- return new PilotLocalDatabase(DOCConduitSettings::pDBDirectory(),
- TQString::fromLatin1(dbinfo.name), false);
- }
- else
- {
- return deviceLink()->database(TQString::fromLatin1(dbinfo.name));
- }
-}
-
-
-// res gives us information whether the sync worked and the db might need to be
-// transferred to the handheld or not (and we just need to clean up the mess)
-bool DOCConduit::postSyncAction(PilotDatabase * database,
- docSyncInfo &sinfo, bool res)
-{
- FUNCTIONSETUP;
- bool rs = true;
-
- switch (sinfo.direction)
- {
- case eSyncPDAToPC:
- // also reset the sync flags on the handheld
-#ifdef DEBUG
- DEBUGKPILOT<<"Resetting sync flags for database "
- <<sinfo.dbinfo.name<<endl;
-#endif
- if (DOCConduitSettings::keepPDBsLocally() && !DOCConduitSettings::localSync())
- {
- PilotDatabase*db=deviceLink()->database(
- TQString::fromLatin1(sinfo.dbinfo.name));
-#ifdef DEBUG
- DEBUGKPILOT<<"Middle 1 Resetting sync flags for database "
- <<sinfo.dbinfo.name<<endl;
-#endif
- if (db)
- {
- db->resetSyncFlags();
- KPILOT_DELETE(db);
- }
- }
-#ifdef DEBUG
- DEBUGKPILOT<<"End Resetting sync flags for database "
- <<sinfo.dbinfo.name<<endl;
-#endif
- break;
- case eSyncPCToPDA:
- if (DOCConduitSettings::keepPDBsLocally() && !DOCConduitSettings::localSync() && res)
- {
- // Copy the database to the palm
- PilotLocalDatabase*localdb=dynamic_cast<PilotLocalDatabase*>(database);
- if (localdb)
- {
-#ifdef DEBUG
- DEBUGKPILOT<<"Installing file "<<localdb->dbPathName()<<" ("
- <<sinfo.handheldDB<<") to the handheld"<<endl;
-#endif
- TQString dbpathname=localdb->dbPathName();
- // This deletes localdb as well, which is just a cast from database
- KPILOT_DELETE(database);
- if (!fHandle->installFiles(dbpathname, false))
- {
- rs = false;
-#ifdef DEBUG
- DEBUGKPILOT<<"Could not install the database "<<dbpathname<<" ("
- <<sinfo.handheldDB<<")"<<endl;
-#endif
- }
- }
- }
- default:
- break;
- }
-
-#ifdef DEBUG
- DEBUGKPILOT<<"Vor KPILOT_DELETE(database)"<<endl;
-#endif
-
- KPILOT_DELETE(database);
-#ifdef DEBUG
- DEBUGKPILOT<<"End postSyncAction"<<endl;
-#endif
- return rs;
-}
-
-
-
-void DOCConduit::cleanup()
-{
- FUNCTIONSETUP;
- DOCConduitSettings::setConvertedDOCfiles( fDBNames );
- DOCConduitSettings::self()->writeConfig();
-
- emit syncDone(this);
-}
-