NAME
Mail::Box::Mbox - Handle folders with many messages per file.
SYNOPSIS
use Mail::Box::Mbox;
my $folder = new Mail::Box::Mbox folder => $ENV{MAIL}, ...;
DESCRIPTION
This manual-page describes Mail::Box::Mbox and Mail::Box::Mbox::* packages. Read Mail::Box::Manager and Mail::Box first.
How Mbox-folders work
Mbox folders store many messages in one file (let's call this a `file-based' folder, in contrary to a `directory-based' foldertype like MH).
In file-based folders, each message is preceeded by a line which starts with the word From
. Lines inside a message which do accedentally start with From
are, in the file, preceeded by `>'. This character is stripped when the message is read.
The name of a folder may be an absolute or relative path. You can also preceed the foldername by =
, which means that it is relative to the folderdir as specified at new
.
Simulation of sub-folders
File-based folders do not really have a sub-folder idea, as directory-based folders have, but this module tries to simulate them. In this implementation a directory like
Mail/subject1/
is taken as an empty folder Mail/subject1
, with the folders in that directory as sub-folders for it. You may also use
Mail/subject1
Mail/subject1.d/
where Mail/subject1
is the folder, and the folders in the Mail/subject1.d
directory are used as sub-folders. If your situation is as in the first example and you want to put messages in that empty folder, the directory is automatically renamed, such that the second situation is reached.
Because of these simulated sub-folders, the folder-manager does not need to distiguish between file- and directory-based folders in this respect.
Message State Transition
The user of a folder gets his hand on a message-object, and is not bothered with the actual data which is stored in the object at that moment. As implementor of a mail-package, you might be.
A message is not a message from the start, but only if you access the body from it. Below is depicted how the internal status of the message-object changes based on actions on the object and parameters.
The Mail::Box::Mbox::Message
stage, means that the whole message is in memory. It then is a full decendent of a MIME::Entity
. But at the same time, it consumes a considerable amount of memory, and spent quite some processor time. All the intermediate stati are created to avoid full loading, so to be cheap in memory and time. Folder access will be much faster under normal circumstances.
For trained eyes only:
read() !lazy
-------> +----------------------------------> Mail::Box::
| Mbox::Message
| ^
| |
| NotParsed load |
| ALL ,-----> NotReadHead ------>-'|
| lazy / |
`--------->+ |
\ NotParsed load |
REAL `-----> MIME::Head ------->-'
,-------------------------+---.
| ALL | | regexps && taken
v | |
NotParsed head() get() / /
NotReadHead --------> ------->+---'
\ \ \
\ other() \ other() \regexps && !taken
\ \ \
\ \ \ load Mail::Box::
`----->----+---------+---------> MBox::Message
,---------------.
| |
v |
NotParsed head() |
MIME::Head -------->--'
\ Mail::Box::
`------------------------> MBox::Message
Terms: lazy
refers to the evaluation of the lazy_extract()
option. The load
and load_head
are triggers to the AUTOLOAD
mothods. All terms like head()
refer to method-calls. Finally, ALL
, REAL
, and regexps
(default) refer to values of the take_headers
option of new()
.
Hm... not that easy... but relatively simple compared to MH-folder messages.
PUBLIC INTERFACE
- new ARGS
-
Create a new folder. Many options are taken from object-classes which Mail::Box::Mbox is an extention of. Read below for a detailed description of Mbox specific options.
access Mail::Box 'r' create Mail::Box 0 dummy_type Mail::Box::Threads 'Mail::Box::Message::Dummy' folder Mail::Box $ENV{MAIL} folderdir Mail::Box $ENV{HOME}.'/Mail' lazy_extract Mail::Box 10kb lockfile Mail::Box::Locker foldername.lock-extention lock_extention Mail::Box::Mbox '.lock' lock_method Mail::Box::Locker 'dotlock' lock_timeout Mail::Box::Locker 1 hour lock_wait Mail::Box::Locker 10 seconds manager Mail::Box undef message_type Mail::Box 'Mail::Box::Mbox::Message' notreadhead_type Mail::Box 'Mail::Box::Message::NotReadHead' notread_type Mail::Box 'Mail::Box::Mbox::Message::NotParsed' realhead_type Mail::Box 'MIME::Head' remove_when_empty Mail::Box 1 save_on_exit Mail::Box 1 subfolder_extention Mail::Box::Mbox '.d' take_headers Mail::Box <quite some> thread_body Mail::Box::Threads 0 thread_timespan Mail::Box::Threads <not used> thread_window Mail::Box::Threads <not used> <none> Mail::Box::Tie
Mbox specific options:
lock_extention => FILENAME|STRING
When the dotlock locking mechanism is used, the lock is created by the creation of a file. For Mail::Box::Mbox type of folders, this file is by default named as the folder-file itself, followed by
.lock
.You may specify an absolute filename, a relative (to the folder's directory) name, or an extention (preceeded by a dot). So valid examples are:
.lock # append to filename my_own_lockfile.test # full filename, same dir /etc/passwd # somewhere else
subfolder_extention => STRING
Mail folders which store their messages in files do usually not support sub-folders, as known by mail folders which store messages in a directory.
However, we simulate sub-directories if the user wants us to. When a subfolder of folder
xyz
is created, we create a directory which is calledxyz.d
to contain them. This extention.d
can be changed using this option.
- fileOpen
- fileIsOpen
- fileClose
-
Open/close the file which keeps the folder. If the folder is already open, it will not be opened again. This method will maintain exclusive locking. Of course,
fileIsOpen
only checks if the file is opened or not.Example:
my $file = $folder->fileOpen or die; $folder->fileClose;
- readMessages
-
Read all messages from the folder. This method is called at instantiation of the folder, so do not call it yourself unless you have a very good reason.
- write
-
Write all messages to the folder-file. Returns the folder when this was successful. If you want to write to a different file, you first create a new folder, then move the messages, and then write that file. As options you may specify (see
Mail::Box
for explanation)keep_deleted => BOOL
save_deleted => BOOL
remove_when_empty => BOOL
- addMessage MESSAGE
-
Add a message to the Mbox-folder. If you specify a message with an id which is already in the folder, the message will be ignored.
- appendMessages OPTIONS
-
(Class method) Append one or more messages to a folder. The folder will not be read, but messages are just appended to the folder-file. This also means that double messages can exist in a folder.
If the folder does not exist,
undef
(or FALSE) is returned.folder => FOLDERNAME
message => MESSAGE
messages => ARRAY-OF-MESSAGES
Example:
my $message = Mail::Internet->new(...); Mail::Box::Mbox->appendMessages ( folder => '=xyz' , message => $message , folderdir => $ENV{FOLDERS} );
- filename
-
Returns the filename related to this folder.
Example:
print $folder->filename;
- folderToFilename FOLDERNAME, FOLDERDIR, EXTENTION
-
(class method) Translate a foldername into a filename, with use of the FOLDERDIR to replace a leading
=
.
folder management methods
Read the Mail::Box manual for more details and more options on each method.
- foundIn FOLDERNAME [,OPTIONS]
-
Autodetect if there is a Mail::Box::Mbox folder specified here. The FOLDERNAME specifies the name of the folder, as is specified by the application. ARGS is a reference to a hash with extra information on the request. For this class, we use (if defined):
folderdir => DIRECTORY
subfolder_extention => STRING
Example:
Mail::Box::Mbox->foundIn ( '=markov' , folderdir => "$ENV{HOME}/Mail" );
- create FOLDERNAME [, OPTIONS]
-
(Class method) Create a folder. If the folder already exists, it will be left untouched. As options, you may specify:
folderdir => DIRECTORY
- listFolders [OPTIONS]
-
(Class OR Instance method) List the folders in a certain directory. This method can be called on the class, in which case you specify the base folder where the sub-folders must be retreived from as name. When used on an instance, the sub-folders of the instance are returned.
Folders will not start with a dot. When a directory without the sub-folder extention is found, then an empty folder is presumed.
folder => FOLDERNAME
folderdir => DIRECTORY
check => BOOL
skip_empty => BOOL
subfolder_extention => STRING
- openSubFolder NAME [,OPTIONS]
-
Open (or create, if it does not exist yet) a new subfolder to an existing folder.
Example:
my $folder = Mail::Box::Mbox->new(folder => '=Inbox'); my $sub = $folder->openSubFolder('read');
Mail::Box::Mbox::Message::Runtime
This object contains methods which are part of as well delay-loaded (not-parsed) as loaded messages, but not general for all folders.
PUBLIC INTERFACE
- new ARGS
-
Messages in file-based folders use the following extra options for creation:
from LINE
The line which precedes each message in the file. Some people detest this line, but this is just how things were invented...
- fromLine [LINE]
-
Many people detest file-style folders because they store messages all in one file, where a line starting with
From
leads the header. If we receive a message from a file-based folder, we store that line. If we write to such a file, but there is no such line stored, then we try to produce one.When you pass a LINE, that this is stored.
- print FILEHANDLE
-
Write one message to a file-handle. Unmodified messages are taken from the folder-file where they were stored in. Modified messages are written as in memory. Specify a FILEHANDLE to write to (defaults to STDOUT).
- migrate FILEHANDLE
-
Move the message from the current folder, to a new folder-file. The old location should be not used after this.
Mail::Box::Mbox::Message
This object extends a Mail::Box::Message with extra tools and facts on what is special to messages in file-based folders, with respect to messages in other types of folders.
PUBLIC INTERFACE
- coerce FOLDER, MESSAGE [,OPTIONS]
-
(Class method) Coerce a MESSAGE into a Mail::Box::Mbox::Message. When any message is offered to be stored in a mbox FOLDER, it first should have all fields which are specific for Mbox-folders.
The coerced message is returned on success, else
undef
.Example:
my $inbox = Mail::Box::Mbox->new(...); my $mh = Mail::Box::MH::Message->new(...); Mail::Box::Mbox::Message->coerce($inbox, $mh); # Now, the $mh is ready to be included in $inbox.
However, you can better use
$inbox->coerce($mh);
which will call the right coerce() for sure.
Mail::Box::Mbox::Message::NotParsed
Not parsed messages stay in the file until the message is used. Because this folder structure uses many messages in the same file, the byte-locations are remembered.
PUBLIC INTERFACE
- load
-
This method is called by the autoloader then the data of the message is required. If you specified
REAL
for thetake_headers
option fornew()
, you did have a MIME::Head in your hands, however this will be destroyed when the whole message is loaded.
AUTHOR
Mark Overmeer (Mark@Overmeer.net). All rights reserved. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself.
VERSION
This code is alpha, version 0.92