Add missing include.
[kdepim.git] / kmailcvt / filter_evolution.cxx
blobae6777d893816d99361b99bd6836c301e4a2bbf4
1 /*
2 * filter_evolution.cxx
3 * Author : Simon MARTIN <simartin@users.sourceforge.net>
4 * Copyright (c) 2004 Simon MARTIN <simartin@users.sourceforge.net>
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU Library General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
21 #include "filter_evolution.hxx"
23 #include <klocale.h>
24 #include <kfiledialog.h>
25 #include <ktemporaryfile.h>
28 /** Default constructor. */
29 FilterEvolution::FilterEvolution(void) :
30 Filter(i18n("Import Evolution 1.x Local Mails and Folder Structure"),
31 "Simon MARTIN<br /><br />( Filter accelerated by Danny Kukawka )",
32 i18n("<p><b>Evolution 1.x import filter</b></p>"
33 "<p>Select the base directory of Evolution's mails (usually ~/evolution/local).</p>"
34 "<p>Since it is possible to recreate the folder structure, the folders "
35 "will be stored under: \"Evolution-Import\".</p>"))
38 /** Destructor. */
39 FilterEvolution::~FilterEvolution(void)
43 /** Recursive import of Evolution's mboxes. */
44 void FilterEvolution::import(FilterInfo *info)
46 // We ask the user to choose Evolution's root directory.
47 QString evolDir = QDir::homePath() + "/evolution/local";
48 QDir d( evolDir );
49 if ( !d.exists() ) {
50 evolDir = QDir::homePath();
53 mailDir = KFileDialog::getExistingDirectory(evolDir, info->parent());
55 if (mailDir.isEmpty()) {
56 info->alert(i18n("No directory selected."));
58 /**
59 * If the user only select homedir no import needed because
60 * there should be no files and we surely import wrong files.
62 else if ( mailDir == QDir::homePath() || mailDir == (QDir::homePath() + '/')) {
63 info->addLog(i18n("No files found for import."));
64 } else {
65 info->setOverall(0);
66 // Recursive import of the MBoxes.
67 QDir dir(mailDir);
68 const QStringList rootSubDirs = dir.entryList(QStringList("[^\\.]*"), QDir::Dirs, QDir::Name); // Removal of . and ..
69 int currentDir = 1, numSubDirs = rootSubDirs.size();
70 for(QStringList::ConstIterator filename = rootSubDirs.constBegin() ; filename != rootSubDirs.constEnd() ; ++filename, ++currentDir) {
71 importDirContents(info, dir.filePath(*filename), *filename, QString());
72 info->setOverall((int) ((float) currentDir / numSubDirs * 100));
75 info->addLog( i18n("Finished importing emails from %1", mailDir ));
76 info->setCurrent(100);
77 info->setOverall(100);
80 /**
81 * Import of a directory contents.
82 * @param info Information storage for the operation.
83 * @param dirName The name of the directory to import.
84 * @param KMailRootDir The directory's root directory in KMail's folder structure.
85 * @param KMailSubDir The directory's direct ancestor in KMail's folder structure.
87 void FilterEvolution::importDirContents(FilterInfo *info, const QString& dirName, const QString& KMailRootDir, const QString& KMailSubDir)
89 // If there is a mbox, we import it
90 QDir dir(dirName);
91 if(dir.exists("mbox")) {
92 importMBox(info, dirName + "/mbox", KMailRootDir, KMailSubDir);
94 // If there are subfolders, we import them one by one
95 if(dir.exists("subfolders")) {
96 QDir subfolders(dirName + "/subfolders");
97 const QStringList subDirs = subfolders.entryList(QStringList("[^\\.]*"), QDir::Dirs, QDir::Name);
98 for(QStringList::ConstIterator filename = subDirs.constBegin() ; filename != subDirs.constEnd() ; ++filename) {
99 QString kSubDir;
100 if(!KMailSubDir.isNull()) {
101 kSubDir = KMailSubDir + '/' + *filename;
102 } else {
103 kSubDir = *filename;
105 importDirContents(info, subfolders.filePath(*filename), KMailRootDir, kSubDir);
111 * Import of a MBox file.
112 * @param info Information storage for the operation.
113 * @param dirName The MBox's name.
114 * @param KMailRootDir The directory's root directory in KMail's folder structure.
115 * @param KMailSubDir The directory's equivalent in KMail's folder structure. *
117 void FilterEvolution::importMBox(FilterInfo *info, const QString& mboxName, const QString& rootDir, const QString& targetDir)
119 QFile mbox(mboxName);
120 bool first_msg = true;
121 QString tmp_from = mboxName;
122 if (!mbox.open(QIODevice::ReadOnly)) {
123 info->alert(i18n("Unable to open %1, skipping", mboxName));
124 } else {
125 QFileInfo filenameInfo(mboxName);
127 info->setCurrent(0);
128 if( mboxName.length() > 20 ) {
129 QString tmp_info = mboxName;
130 tmp_info = tmp_info.replace( mailDir, ".." );
131 if (tmp_info.contains("subfolders/"))
132 tmp_info.remove("subfolders/");
133 info->setFrom( tmp_info );
134 tmp_from = tmp_info;
135 } else
136 info->setFrom(mboxName);
137 if(targetDir.contains("subfolders/")) {
138 QString tmp_info = targetDir;
139 tmp_info.remove("subfolders/");
140 info->setTo(tmp_info);
141 } else
142 info->setTo(targetDir);
144 info->addLog(i18n("Importing emails from %1...", tmp_from));
146 QByteArray input(MAX_LINE,'\0');
147 long l = 0;
149 while (!mbox.atEnd()) {
150 KTemporaryFile tmp;
151 tmp.open();
152 /* comment by Danny:
153 * Don't use QTextStream to read from mbox, better use QDataStream. QTextStream only
154 * support Unicode/Latin1/Locale. So you lost information from emails with
155 * charset!=Unicode/Latin1/Locale (e.g. KOI8-R) and Content-Transfer-Encoding != base64
156 * (e.g. 8Bit). It also not help to convert the QTextStream to Unicode. By this you
157 * get Unicode/UTF-email but KMail can't detect the correct charset.
159 QByteArray separate;
161 if(!first_msg)
162 tmp.write( input, l );
163 l = mbox.readLine( input.data(),MAX_LINE); // read the first line, prevent "From "
164 tmp.write( input, l );
166 while ( ! mbox.atEnd() && (l = mbox.readLine(input.data(),MAX_LINE)) && ((separate = input.data()).left(5) != "From ")) {
167 tmp.write( input, l );
169 tmp.flush();
170 first_msg = false;
172 QString destFolder = rootDir;
173 if(!targetDir.isNull()) {
174 destFolder = "Evolution-Import/" + destFolder + '/' + targetDir;
175 } else {
176 destFolder = "Evolution-Import/" + destFolder;
179 /* comment by Danny Kukawka:
180 * addMessage() == old function, need more time and check for duplicates
181 * addMessage_fastImport == new function, faster and no check for duplicates
183 if(info->removeDupMsg)
184 addMessage( info, destFolder, tmp.fileName() );
185 else
186 addMessage_fastImport( info, destFolder, tmp.fileName() );
188 int currentPercentage = (int) (((float) mbox.pos() / filenameInfo.size()) * 100);
189 info->setCurrent(currentPercentage);
190 if (info->shouldTerminate()) return;
193 if (count_duplicates > 0) {
194 info->addLog( i18np("1 duplicate message not imported", "%1 duplicate messages not imported", count_duplicates));
196 count_duplicates = 0;
197 mbox.close();