Maildir to zmmailbox with bash: Difference between revisions
No edit summary |
No edit summary |
||
Line 1: | Line 1: | ||
== What's new == | |||
I decided to rewrite Jarosław's script to fix a few bugs I stumbled upon while migrating my bare-Postfix server to Zimbra, namely: | |||
* all folders were merged into the main folder due to a bug in the script (hint: '=' instead of '=='). | |||
* folders with spaces in their name were not imported and caused an error | |||
* import messages from accounts across multiple domains, if needed | |||
* made the code readable | |||
* no need for two loops | |||
== How to use == | |||
The script expects to find the mailboxes in the current path! The structure of maildirs must be as follows: | |||
domain/username/{cur|new|tmp} | |||
domain/username/subfolder1/{cur|new|tmp} | |||
domain/username/subfolder2/{cur|new|tmp} | |||
... | |||
After the script has run, every zimbra user will have a subfolder in his mailbox called 'old-mbox' (feel free to change the name at the beginning of the script). | |||
The hierarchy of subfolders is maintained under old-mbox. | |||
== The code == | |||
<pre> | |||
#!/bin/bash | |||
# Postfix virtual transport -> Zimbra mailbox migration | |||
# written by NERvOus (http://www.nervous.it) | |||
# base folder where msgs will be imported | |||
BFOLDER="old-mbox" | |||
ZMMBOX="/opt/zimbra/bin/zmmailbox" | |||
BDIR=$(pwd) | |||
echo You must run $0 from inside /var/mail/virtual directory | |||
echo $0 expects to find the mailboxes in the current path! | |||
echo The structure of maildirs must be as follows: | |||
echo | |||
echo "domain/username/{cur|new|tmp}" | |||
echo "domain/username/subfolder1/{cur|new|tmp}" | |||
echo "domain/username/subfolder2/{cur|new|tmp}" | |||
echo ... | |||
echo | |||
echo All folders will be stored in a subfolder called $BFOLDER | |||
echo The hierarchy of subfolders will be maintained under $BFOLDER. | |||
echo | |||
echo Press Enter to start, CTRL+C to abort. | |||
read | |||
# handle folders with a space inside, they are more common than you may | |||
# think | |||
IFS=' | |||
' | |||
for p in $(find . -type d -name cur); do | |||
DOMAIN=`echo $p | cut -d'/' -f2` | |||
UNAME=`echo $p | cut -d'/' -f3` | |||
DIRNAME=`echo $p | cut -d'/' -f4` | |||
# this may fail, if folder already exists. Who cares. Ignore the | |||
# error. | |||
echo createFolder /$BFOLDER | $ZMMBOX -z -m $UNAME@$DOMAIN | |||
if [ "$DIRNAME" == "cur" ]; then | |||
echo Importing INBOX folder for $UNAME@$DOMAIN from $BDIR/$DOMAIN/$UNAME/ 1>&2 | |||
# we are importing the top level folder | |||
echo addMessage /$BFOLDER $BDIR/$DOMAIN/$UNAME/cur | $ZMMBOX -z -m $UNAME@$DOMAIN | |||
echo addMessage /$BFOLDER $BDIR/$DOMAIN/$UNAME/new | $ZMMBOX -z -m $UNAME@$DOMAIN | |||
else | else | ||
DIRNAME=$(echo $DIRNAME | sed -e 's/\/cur$//') | |||
echo Importing folder $DIRNAME for $UNAME@$DOMAIN from $BDIR/$DOMAIN/$UNAME/$DIRNAME 1>&2 | |||
echo createFolder \'/$BFOLDER/$DIRNAME\' | $ZMMBOX -z -m $UNAME@$DOMAIN | |||
echo addMessage \'/$BFOLDER/$DIRNAME\' \'$BDIR/$DOMAIN/$UNAME/$DIRNAME/cur\' | $ZMMBOX -z -m $UNAME@$DOMAIN | |||
echo addMessage \'/$BFOLDER/$DIRNAME\' \'$BDIR/$DOMAIN/$UNAME/$DIRNAME/new\' | $ZMMBOX -z -m $UNAME@$DOMAIN | |||
fi | |||
done | done | ||
</pre> | </pre> | ||
[[Category:Migration]] | [[Category:Migration]] |
Revision as of 17:53, 20 December 2009
What's new
I decided to rewrite Jarosław's script to fix a few bugs I stumbled upon while migrating my bare-Postfix server to Zimbra, namely:
- all folders were merged into the main folder due to a bug in the script (hint: '=' instead of '==').
- folders with spaces in their name were not imported and caused an error
- import messages from accounts across multiple domains, if needed
- made the code readable
- no need for two loops
How to use
The script expects to find the mailboxes in the current path! The structure of maildirs must be as follows:
domain/username/{cur|new|tmp} domain/username/subfolder1/{cur|new|tmp} domain/username/subfolder2/{cur|new|tmp} ...
After the script has run, every zimbra user will have a subfolder in his mailbox called 'old-mbox' (feel free to change the name at the beginning of the script). The hierarchy of subfolders is maintained under old-mbox.
The code
#!/bin/bash # Postfix virtual transport -> Zimbra mailbox migration # written by NERvOus (http://www.nervous.it) # base folder where msgs will be imported BFOLDER="old-mbox" ZMMBOX="/opt/zimbra/bin/zmmailbox" BDIR=$(pwd) echo You must run $0 from inside /var/mail/virtual directory echo $0 expects to find the mailboxes in the current path! echo The structure of maildirs must be as follows: echo echo "domain/username/{cur|new|tmp}" echo "domain/username/subfolder1/{cur|new|tmp}" echo "domain/username/subfolder2/{cur|new|tmp}" echo ... echo echo All folders will be stored in a subfolder called $BFOLDER echo The hierarchy of subfolders will be maintained under $BFOLDER. echo echo Press Enter to start, CTRL+C to abort. read # handle folders with a space inside, they are more common than you may # think IFS=' ' for p in $(find . -type d -name cur); do DOMAIN=`echo $p | cut -d'/' -f2` UNAME=`echo $p | cut -d'/' -f3` DIRNAME=`echo $p | cut -d'/' -f4` # this may fail, if folder already exists. Who cares. Ignore the # error. echo createFolder /$BFOLDER | $ZMMBOX -z -m $UNAME@$DOMAIN if [ "$DIRNAME" == "cur" ]; then echo Importing INBOX folder for $UNAME@$DOMAIN from $BDIR/$DOMAIN/$UNAME/ 1>&2 # we are importing the top level folder echo addMessage /$BFOLDER $BDIR/$DOMAIN/$UNAME/cur | $ZMMBOX -z -m $UNAME@$DOMAIN echo addMessage /$BFOLDER $BDIR/$DOMAIN/$UNAME/new | $ZMMBOX -z -m $UNAME@$DOMAIN else DIRNAME=$(echo $DIRNAME | sed -e 's/\/cur$//') echo Importing folder $DIRNAME for $UNAME@$DOMAIN from $BDIR/$DOMAIN/$UNAME/$DIRNAME 1>&2 echo createFolder \'/$BFOLDER/$DIRNAME\' | $ZMMBOX -z -m $UNAME@$DOMAIN echo addMessage \'/$BFOLDER/$DIRNAME\' \'$BDIR/$DOMAIN/$UNAME/$DIRNAME/cur\' | $ZMMBOX -z -m $UNAME@$DOMAIN echo addMessage \'/$BFOLDER/$DIRNAME\' \'$BDIR/$DOMAIN/$UNAME/$DIRNAME/new\' | $ZMMBOX -z -m $UNAME@$DOMAIN fi done