Added support for SPECIAL-USE extension (IMAP).
This commit is contained in:
parent
1791e5114a
commit
bd378bbfa2
@ -36,6 +36,18 @@ namespace vmime {
|
|||||||
namespace net {
|
namespace net {
|
||||||
|
|
||||||
|
|
||||||
|
int folder::getType()
|
||||||
|
{
|
||||||
|
return getAttributes().getType();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int folder::getFlags()
|
||||||
|
{
|
||||||
|
return getAttributes().getFlags();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void folder::addMessageChangedListener(events::messageChangedListener* l)
|
void folder::addMessageChangedListener(events::messageChangedListener* l)
|
||||||
{
|
{
|
||||||
m_messageChangedListeners.push_back(l);
|
m_messageChangedListeners.push_back(l);
|
||||||
|
@ -42,6 +42,7 @@
|
|||||||
#include "vmime/net/events.hpp"
|
#include "vmime/net/events.hpp"
|
||||||
#include "vmime/net/folderStatus.hpp"
|
#include "vmime/net/folderStatus.hpp"
|
||||||
#include "vmime/net/fetchAttributes.hpp"
|
#include "vmime/net/fetchAttributes.hpp"
|
||||||
|
#include "vmime/net/folderAttributes.hpp"
|
||||||
|
|
||||||
#include "vmime/utility/path.hpp"
|
#include "vmime/utility/path.hpp"
|
||||||
#include "vmime/utility/stream.hpp"
|
#include "vmime/utility/stream.hpp"
|
||||||
@ -91,33 +92,28 @@ public:
|
|||||||
MODE_READ_WRITE /**< Full access mode (read and write). */
|
MODE_READ_WRITE /**< Full access mode (read and write). */
|
||||||
};
|
};
|
||||||
|
|
||||||
/** Folder types.
|
|
||||||
*/
|
|
||||||
enum Types
|
|
||||||
{
|
|
||||||
TYPE_CONTAINS_FOLDERS = (1 << 0), /**< Folder can contain folders. */
|
|
||||||
TYPE_CONTAINS_MESSAGES = (1 << 1) /**< Folder can contain messages. */
|
|
||||||
};
|
|
||||||
|
|
||||||
/** Folder flags.
|
|
||||||
*/
|
|
||||||
enum Flags
|
|
||||||
{
|
|
||||||
FLAG_HAS_CHILDREN = (1 << 0), /**< Folder contains subfolders. */
|
|
||||||
FLAG_NO_OPEN = (1 << 1) /**< Folder cannot be open. */
|
|
||||||
};
|
|
||||||
|
|
||||||
/** Return the type of this folder.
|
/** Return the type of this folder.
|
||||||
*
|
*
|
||||||
* @return folder type (see folder::Types)
|
* \deprecated Use the getAttributes().getType() method instead
|
||||||
|
*
|
||||||
|
* @return folder type (see folderAttributes::Types enum)
|
||||||
*/
|
*/
|
||||||
virtual int getType() = 0;
|
int getType();
|
||||||
|
|
||||||
/** Return the flags of this folder.
|
/** Return the flags of this folder.
|
||||||
*
|
*
|
||||||
* @return folder flags (see folder::Flags)
|
* \deprecated Use the getAttributes().getFlags() method instead
|
||||||
|
*
|
||||||
|
* @return folder flags (see folderAttributes::Flags enum)
|
||||||
*/
|
*/
|
||||||
virtual int getFlags() = 0;
|
int getFlags();
|
||||||
|
|
||||||
|
/** Return the attributes of the folder.
|
||||||
|
*
|
||||||
|
* @return folder attributes (see folder::Flags)
|
||||||
|
*/
|
||||||
|
virtual const folderAttributes getAttributes() = 0;
|
||||||
|
|
||||||
/** Return the mode in which the folder has been open.
|
/** Return the mode in which the folder has been open.
|
||||||
*
|
*
|
||||||
@ -159,10 +155,10 @@ public:
|
|||||||
|
|
||||||
/** Create this folder.
|
/** Create this folder.
|
||||||
*
|
*
|
||||||
* @param type folder type (see folder::Types)
|
* @param attribs attributes of the new folder
|
||||||
* @throw exceptions::net_exception if an error occurs
|
* @throw exceptions::net_exception if an error occurs
|
||||||
*/
|
*/
|
||||||
virtual void create(const int type) = 0;
|
virtual void create(const folderAttributes& attribs) = 0;
|
||||||
|
|
||||||
/** Test whether this folder exists.
|
/** Test whether this folder exists.
|
||||||
*
|
*
|
||||||
|
121
src/vmime/net/folderAttributes.cpp
Normal file
121
src/vmime/net/folderAttributes.cpp
Normal file
@ -0,0 +1,121 @@
|
|||||||
|
//
|
||||||
|
// VMime library (http://www.vmime.org)
|
||||||
|
// Copyright (C) 2002-2014 Vincent Richard <vincent@vmime.org>
|
||||||
|
//
|
||||||
|
// 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 3 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; if not, write to the Free Software Foundation, Inc.,
|
||||||
|
// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||||
|
//
|
||||||
|
// Linking this library statically or dynamically with other modules is making
|
||||||
|
// a combined work based on this library. Thus, the terms and conditions of
|
||||||
|
// the GNU General Public License cover the whole combination.
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "vmime/config.hpp"
|
||||||
|
|
||||||
|
|
||||||
|
#if VMIME_HAVE_MESSAGING_FEATURES
|
||||||
|
|
||||||
|
|
||||||
|
#include "vmime/net/folderAttributes.hpp"
|
||||||
|
|
||||||
|
#include <algorithm>
|
||||||
|
|
||||||
|
|
||||||
|
namespace vmime {
|
||||||
|
namespace net {
|
||||||
|
|
||||||
|
|
||||||
|
folderAttributes::folderAttributes()
|
||||||
|
: m_type(TYPE_CONTAINS_FOLDERS | TYPE_CONTAINS_MESSAGES),
|
||||||
|
m_flags(0),
|
||||||
|
m_specialUse(SPECIALUSE_NONE)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
folderAttributes::folderAttributes(const folderAttributes& attribs)
|
||||||
|
: m_type(attribs.m_type),
|
||||||
|
m_flags(attribs.m_flags),
|
||||||
|
m_userFlags(attribs.m_userFlags),
|
||||||
|
m_specialUse(attribs.m_specialUse)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int folderAttributes::getType() const
|
||||||
|
{
|
||||||
|
return m_type;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void folderAttributes::setType(const int type)
|
||||||
|
{
|
||||||
|
m_type = type;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int folderAttributes::getSpecialUse() const
|
||||||
|
{
|
||||||
|
return m_specialUse;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void folderAttributes::setSpecialUse(const int use)
|
||||||
|
{
|
||||||
|
m_specialUse = use;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
int folderAttributes::getFlags() const
|
||||||
|
{
|
||||||
|
return m_flags;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void folderAttributes::setFlags(const int flags)
|
||||||
|
{
|
||||||
|
m_flags = flags;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool folderAttributes::hasFlag(const int flag)
|
||||||
|
{
|
||||||
|
return (m_flags & flag) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
const std::vector <string> folderAttributes::getUserFlags() const
|
||||||
|
{
|
||||||
|
return m_userFlags;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void folderAttributes::setUserFlags(const std::vector <string>& flags)
|
||||||
|
{
|
||||||
|
m_userFlags = flags;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
bool folderAttributes::hasUserFlag(const string& flag)
|
||||||
|
{
|
||||||
|
return std::find(m_userFlags.begin(), m_userFlags.end(), flag) != m_userFlags.end();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
} // net
|
||||||
|
} // vmime
|
||||||
|
|
||||||
|
|
||||||
|
#endif // VMIME_HAVE_MESSAGING_FEATURES
|
||||||
|
|
179
src/vmime/net/folderAttributes.hpp
Normal file
179
src/vmime/net/folderAttributes.hpp
Normal file
@ -0,0 +1,179 @@
|
|||||||
|
//
|
||||||
|
// VMime library (http://www.vmime.org)
|
||||||
|
// Copyright (C) 2002-2014 Vincent Richard <vincent@vmime.org>
|
||||||
|
//
|
||||||
|
// 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 3 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; if not, write to the Free Software Foundation, Inc.,
|
||||||
|
// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||||
|
//
|
||||||
|
// Linking this library statically or dynamically with other modules is making
|
||||||
|
// a combined work based on this library. Thus, the terms and conditions of
|
||||||
|
// the GNU General Public License cover the whole combination.
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef VMIME_NET_FOLDERATTRIBUTES_HPP_INCLUDED
|
||||||
|
#define VMIME_NET_FOLDERATTRIBUTES_HPP_INCLUDED
|
||||||
|
|
||||||
|
|
||||||
|
#include "vmime/config.hpp"
|
||||||
|
|
||||||
|
|
||||||
|
#if VMIME_HAVE_MESSAGING_FEATURES
|
||||||
|
|
||||||
|
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
#include "vmime/types.hpp"
|
||||||
|
|
||||||
|
|
||||||
|
namespace vmime {
|
||||||
|
namespace net {
|
||||||
|
|
||||||
|
|
||||||
|
/** Holds a set of attributes for a folder.
|
||||||
|
*/
|
||||||
|
class VMIME_EXPORT folderAttributes : public object
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
|
||||||
|
/** Folder types.
|
||||||
|
*/
|
||||||
|
enum Types
|
||||||
|
{
|
||||||
|
TYPE_CONTAINS_FOLDERS = (1 << 0), /**< Folder can contain folders. */
|
||||||
|
TYPE_CONTAINS_MESSAGES = (1 << 1) /**< Folder can contain messages. */
|
||||||
|
};
|
||||||
|
|
||||||
|
/** Folder flags.
|
||||||
|
*/
|
||||||
|
enum Flags
|
||||||
|
{
|
||||||
|
FLAG_HAS_CHILDREN = (1 << 0), /**< Folder contains subfolders. */
|
||||||
|
FLAG_NO_OPEN = (1 << 1) /**< Folder cannot be open. */
|
||||||
|
};
|
||||||
|
|
||||||
|
/** Folder special uses.
|
||||||
|
* Not all protocols support this. At the current time, only IMAP supports this,
|
||||||
|
* if the server has the SPECIAL-USE capability.
|
||||||
|
*/
|
||||||
|
enum SpecialUses
|
||||||
|
{
|
||||||
|
SPECIALUSE_NONE, /**< User folder, no special use (or unknown). */
|
||||||
|
SPECIALUSE_ALL, /**< Virtual folder containing all messages. */
|
||||||
|
SPECIALUSE_ARCHIVE, /**< Folder is used to archives messages (server-dependent). */
|
||||||
|
SPECIALUSE_DRAFTS, /**< Folder is used to hold draft messages - typically, messages
|
||||||
|
that are being composed but have not yet been sent. */
|
||||||
|
SPECIALUSE_FLAGGED, /**< Virtual folder containing all messages which are marked
|
||||||
|
in some way as "important" or "flagged". */
|
||||||
|
SPECIALUSE_JUNK, /**< Folder is used to hold junk mail. */
|
||||||
|
SPECIALUSE_SENT, /**< Folder is is used to hold copies of messages that have
|
||||||
|
been sent. */
|
||||||
|
SPECIALUSE_TRASH, /**< Folder is used to hold messages that have been deleted or
|
||||||
|
marked for deletion (may be a virtual folder). */
|
||||||
|
SPECIALUSE_IMPORTANT /**< Folder contains messages that are likely important to the
|
||||||
|
user. */
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/** Construct a new folderAttributes object with the default set of attributes.
|
||||||
|
*/
|
||||||
|
folderAttributes();
|
||||||
|
|
||||||
|
/** Construct a new folderAttributes object by copying an existing object.
|
||||||
|
*
|
||||||
|
* @param attribs object to copy
|
||||||
|
*/
|
||||||
|
folderAttributes(const folderAttributes& attribs);
|
||||||
|
|
||||||
|
/** Return the type of the folder.
|
||||||
|
*
|
||||||
|
* @return combination of one ore more folder types (see folderAttributes::Types enum)
|
||||||
|
*/
|
||||||
|
int getType() const;
|
||||||
|
|
||||||
|
/** Set the type of the folder.
|
||||||
|
*
|
||||||
|
* @param type combination of one ore more folder types (see folderAttributes::Types enum)
|
||||||
|
*/
|
||||||
|
void setType(const int type);
|
||||||
|
|
||||||
|
/** Return the special use of the folder.
|
||||||
|
* Not all protocols support this. At the current time, only IMAP supports this,
|
||||||
|
* if the server has the SPECIAL-USE capability.
|
||||||
|
*
|
||||||
|
* @return a value which indicates a special use (see folderAttributes::SpecialUses enum)
|
||||||
|
*/
|
||||||
|
int getSpecialUse() const;
|
||||||
|
|
||||||
|
/** Set the special use of the folder.
|
||||||
|
* Not all protocols support this. At the current time, only IMAP supports this,
|
||||||
|
* if the server has the SPECIAL-USE capability.
|
||||||
|
*
|
||||||
|
* @param use a value which indicates a special use (see folderAttributes::SpecialUses enum)
|
||||||
|
*/
|
||||||
|
void setSpecialUse(const int use);
|
||||||
|
|
||||||
|
/** Return the standard (non-user) flags of the folder.
|
||||||
|
*
|
||||||
|
* @return combination of one ore more folder flags (see folderAttributes::Flags enum)
|
||||||
|
*/
|
||||||
|
int getFlags() const;
|
||||||
|
|
||||||
|
/** Set the standard (non-user) flags of the folder.
|
||||||
|
*
|
||||||
|
* @param type combination of one ore more folder flags (see folderAttributes::Flags enum)
|
||||||
|
*/
|
||||||
|
void setFlags(const int flags);
|
||||||
|
|
||||||
|
/** Return whether the specified folder flag(s) is/are set.
|
||||||
|
*
|
||||||
|
* @param flag combination of one ore more folder flags (see folderAttributes::Flags enum)
|
||||||
|
* @return true if the specified flags are all set, or false otherwise
|
||||||
|
*/
|
||||||
|
bool hasFlag(const int flag);
|
||||||
|
|
||||||
|
/** Set the user-defined flags of the folder.
|
||||||
|
*
|
||||||
|
* @return a list of user-defined flags
|
||||||
|
*/
|
||||||
|
const std::vector <string> getUserFlags() const;
|
||||||
|
|
||||||
|
/** Set the user-defined flags of the folder.
|
||||||
|
*
|
||||||
|
* @param flags a list of user-defined flags
|
||||||
|
*/
|
||||||
|
void setUserFlags(const std::vector <string>& flags);
|
||||||
|
|
||||||
|
/** Return whether the specified user-defined flag is set.
|
||||||
|
*
|
||||||
|
* @return true if the specified flag is set, or false otherwise
|
||||||
|
*/
|
||||||
|
bool hasUserFlag(const string& flag);
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
int m_type;
|
||||||
|
int m_flags;
|
||||||
|
std::vector <string> m_userFlags;
|
||||||
|
int m_specialUse;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
} // net
|
||||||
|
} // vmime
|
||||||
|
|
||||||
|
|
||||||
|
#endif // VMIME_HAVE_MESSAGING_FEATURES
|
||||||
|
|
||||||
|
|
||||||
|
#endif // VMIME_NET_FOLDERATTRIBUTES_HPP_INCLUDED
|
@ -51,10 +51,10 @@ namespace net {
|
|||||||
namespace imap {
|
namespace imap {
|
||||||
|
|
||||||
|
|
||||||
IMAPFolder::IMAPFolder(const folder::path& path, shared_ptr <IMAPStore> store, const int type, const int flags)
|
IMAPFolder::IMAPFolder(const folder::path& path, shared_ptr <IMAPStore> store, shared_ptr <folderAttributes> attribs)
|
||||||
: m_store(store), m_connection(store->connection()), m_path(path),
|
: m_store(store), m_connection(store->connection()), m_path(path),
|
||||||
m_name(path.isEmpty() ? folder::path::component("") : path.getLastComponent()), m_mode(-1),
|
m_name(path.isEmpty() ? folder::path::component("") : path.getLastComponent()), m_mode(-1),
|
||||||
m_open(false), m_type(type), m_flags(flags)
|
m_open(false), m_attribs(attribs)
|
||||||
{
|
{
|
||||||
store->registerFolder(this);
|
store->registerFolder(this);
|
||||||
|
|
||||||
@ -90,7 +90,7 @@ int IMAPFolder::getMode() const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int IMAPFolder::getType()
|
const folderAttributes IMAPFolder::getAttributes()
|
||||||
{
|
{
|
||||||
if (!isOpen())
|
if (!isOpen())
|
||||||
throw exceptions::illegal_state("Folder not open");
|
throw exceptions::illegal_state("Folder not open");
|
||||||
@ -98,34 +98,18 @@ int IMAPFolder::getType()
|
|||||||
// Root folder
|
// Root folder
|
||||||
if (m_path.isEmpty())
|
if (m_path.isEmpty())
|
||||||
{
|
{
|
||||||
return (TYPE_CONTAINS_FOLDERS);
|
folderAttributes attribs;
|
||||||
|
attribs.setType(folderAttributes::TYPE_CONTAINS_FOLDERS);
|
||||||
|
attribs.setFlags(folderAttributes::FLAG_HAS_CHILDREN | folderAttributes::FLAG_NO_OPEN);
|
||||||
|
|
||||||
|
return attribs;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (m_type == TYPE_UNDEFINED)
|
if (!m_attribs)
|
||||||
testExistAndGetType();
|
testExistAndGetType();
|
||||||
|
|
||||||
return (m_type);
|
return *m_attribs;
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int IMAPFolder::getFlags()
|
|
||||||
{
|
|
||||||
if (!isOpen())
|
|
||||||
throw exceptions::illegal_state("Folder not open");
|
|
||||||
|
|
||||||
// Root folder
|
|
||||||
if (m_path.isEmpty())
|
|
||||||
{
|
|
||||||
return (FLAG_HAS_CHILDREN | FLAG_NO_OPEN);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (m_flags == FLAG_UNDEFINED)
|
|
||||||
testExistAndGetType();
|
|
||||||
|
|
||||||
return (m_flags);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -245,11 +229,11 @@ void IMAPFolder::open(const int mode, bool failIfModeIsNotAvailable)
|
|||||||
|
|
||||||
case IMAPParser::mailbox_data::FLAGS:
|
case IMAPParser::mailbox_data::FLAGS:
|
||||||
{
|
{
|
||||||
m_type = IMAPUtils::folderTypeFromFlags
|
if (!m_attribs)
|
||||||
(responseData->mailbox_data()->mailbox_flag_list());
|
m_attribs = make_shared <folderAttributes>();
|
||||||
|
|
||||||
m_flags = IMAPUtils::folderFlagsFromFlags
|
IMAPUtils::mailboxFlagsToFolderAttributes
|
||||||
(connection, responseData->mailbox_data()->mailbox_flag_list());
|
(connection, responseData->mailbox_data()->mailbox_flag_list(), *m_attribs);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -338,7 +322,7 @@ void IMAPFolder::onClose()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void IMAPFolder::create(const int type)
|
void IMAPFolder::create(const folderAttributes& attribs)
|
||||||
{
|
{
|
||||||
shared_ptr <IMAPStore> store = m_store.lock();
|
shared_ptr <IMAPStore> store = m_store.lock();
|
||||||
|
|
||||||
@ -361,12 +345,36 @@ void IMAPFolder::create(const int type)
|
|||||||
string mailbox = IMAPUtils::pathToString
|
string mailbox = IMAPUtils::pathToString
|
||||||
(m_connection->hierarchySeparator(), getFullPath());
|
(m_connection->hierarchySeparator(), getFullPath());
|
||||||
|
|
||||||
if (type & TYPE_CONTAINS_FOLDERS)
|
if (attribs.getType() & folderAttributes::TYPE_CONTAINS_FOLDERS)
|
||||||
mailbox += m_connection->hierarchySeparator();
|
mailbox += m_connection->hierarchySeparator();
|
||||||
|
|
||||||
std::ostringstream oss;
|
std::ostringstream oss;
|
||||||
oss << "CREATE " << IMAPUtils::quoteString(mailbox);
|
oss << "CREATE " << IMAPUtils::quoteString(mailbox);
|
||||||
|
|
||||||
|
if (attribs.getSpecialUse() != folderAttributes::SPECIALUSE_NONE)
|
||||||
|
{
|
||||||
|
if (!m_connection->hasCapability("CREATE-SPECIAL-USE"))
|
||||||
|
throw exceptions::operation_not_supported();
|
||||||
|
|
||||||
|
// C: t2 CREATE MySpecial (USE (\Drafts \Sent))
|
||||||
|
oss << "(USE (";
|
||||||
|
|
||||||
|
switch (attribs.getSpecialUse())
|
||||||
|
{
|
||||||
|
case folderAttributes::SPECIALUSE_NONE: // should not happen
|
||||||
|
case folderAttributes::SPECIALUSE_ALL: oss << "\\All"; break;
|
||||||
|
case folderAttributes::SPECIALUSE_ARCHIVE: oss << "\\Archive"; break;
|
||||||
|
case folderAttributes::SPECIALUSE_DRAFTS: oss << "\\Drafts"; break;
|
||||||
|
case folderAttributes::SPECIALUSE_FLAGGED: oss << "\\Flagged"; break;
|
||||||
|
case folderAttributes::SPECIALUSE_JUNK: oss << "\\Junk"; break;
|
||||||
|
case folderAttributes::SPECIALUSE_SENT: oss << "\\Sent"; break;
|
||||||
|
case folderAttributes::SPECIALUSE_TRASH: oss << "\\Trash"; break;
|
||||||
|
case folderAttributes::SPECIALUSE_IMPORTANT: oss << "\\Important"; break;
|
||||||
|
}
|
||||||
|
|
||||||
|
oss << "))";
|
||||||
|
}
|
||||||
|
|
||||||
m_connection->send(true, oss.str(), true);
|
m_connection->send(true, oss.str(), true);
|
||||||
|
|
||||||
|
|
||||||
@ -434,14 +442,12 @@ bool IMAPFolder::exists()
|
|||||||
if (!isOpen() && !store)
|
if (!isOpen() && !store)
|
||||||
throw exceptions::illegal_state("Store disconnected");
|
throw exceptions::illegal_state("Store disconnected");
|
||||||
|
|
||||||
return (testExistAndGetType() != TYPE_UNDEFINED);
|
return testExistAndGetType() != -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int IMAPFolder::testExistAndGetType()
|
int IMAPFolder::testExistAndGetType()
|
||||||
{
|
{
|
||||||
m_type = TYPE_UNDEFINED;
|
|
||||||
|
|
||||||
// To test whether a folder exists, we simple list it using
|
// To test whether a folder exists, we simple list it using
|
||||||
// the "LIST" command, and there should be one unique mailbox
|
// the "LIST" command, and there should be one unique mailbox
|
||||||
// with this name...
|
// with this name...
|
||||||
@ -482,6 +488,9 @@ int IMAPFolder::testExistAndGetType()
|
|||||||
const std::vector <IMAPParser::continue_req_or_response_data*>& respDataList =
|
const std::vector <IMAPParser::continue_req_or_response_data*>& respDataList =
|
||||||
resp->continue_req_or_response_data();
|
resp->continue_req_or_response_data();
|
||||||
|
|
||||||
|
folderAttributes attribs;
|
||||||
|
attribs.setType(-1);
|
||||||
|
|
||||||
for (std::vector <IMAPParser::continue_req_or_response_data*>::const_iterator
|
for (std::vector <IMAPParser::continue_req_or_response_data*>::const_iterator
|
||||||
it = respDataList.begin() ; it != respDataList.end() ; ++it)
|
it = respDataList.begin() ; it != respDataList.end() ; ++it)
|
||||||
{
|
{
|
||||||
@ -498,15 +507,14 @@ int IMAPFolder::testExistAndGetType()
|
|||||||
if (mailboxData != NULL && mailboxData->type() == IMAPParser::mailbox_data::LIST)
|
if (mailboxData != NULL && mailboxData->type() == IMAPParser::mailbox_data::LIST)
|
||||||
{
|
{
|
||||||
// Get the folder type/flags at the same time
|
// Get the folder type/flags at the same time
|
||||||
m_type = IMAPUtils::folderTypeFromFlags
|
IMAPUtils::mailboxFlagsToFolderAttributes
|
||||||
(mailboxData->mailbox_list()->mailbox_flag_list());
|
(m_connection, mailboxData->mailbox_list()->mailbox_flag_list(), attribs);
|
||||||
|
|
||||||
m_flags = IMAPUtils::folderFlagsFromFlags
|
|
||||||
(m_connection, mailboxData->mailbox_list()->mailbox_flag_list());
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return (m_type);
|
m_attribs = make_shared <folderAttributes>(attribs);
|
||||||
|
|
||||||
|
return m_attribs->getType();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -656,7 +664,7 @@ shared_ptr <folder> IMAPFolder::getFolder(const folder::path::component& name)
|
|||||||
if (!store)
|
if (!store)
|
||||||
throw exceptions::illegal_state("Store disconnected");
|
throw exceptions::illegal_state("Store disconnected");
|
||||||
|
|
||||||
return make_shared <IMAPFolder>(m_path / name, store);
|
return make_shared <IMAPFolder>(m_path / name, store, shared_ptr <folderAttributes>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -740,9 +748,11 @@ std::vector <shared_ptr <folder> > IMAPFolder::getFolders(const bool recursive)
|
|||||||
const class IMAPParser::mailbox_flag_list* mailbox_flag_list =
|
const class IMAPParser::mailbox_flag_list* mailbox_flag_list =
|
||||||
mailboxData->mailbox_list()->mailbox_flag_list();
|
mailboxData->mailbox_list()->mailbox_flag_list();
|
||||||
|
|
||||||
v.push_back(make_shared <IMAPFolder>(path, store,
|
shared_ptr <folderAttributes> attribs = make_shared <folderAttributes>();
|
||||||
IMAPUtils::folderTypeFromFlags(mailbox_flag_list),
|
IMAPUtils::mailboxFlagsToFolderAttributes
|
||||||
IMAPUtils::folderFlagsFromFlags(m_connection, mailbox_flag_list)));
|
(m_connection, mailbox_flag_list, *attribs);
|
||||||
|
|
||||||
|
v.push_back(make_shared <IMAPFolder>(path, store, attribs));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -867,7 +877,7 @@ shared_ptr <folder> IMAPFolder::getParent()
|
|||||||
if (m_path.isEmpty())
|
if (m_path.isEmpty())
|
||||||
return null;
|
return null;
|
||||||
else
|
else
|
||||||
return make_shared <IMAPFolder>(m_path.getParent(), m_store.lock());
|
return make_shared <IMAPFolder>(m_path.getParent(), m_store.lock(), shared_ptr <folderAttributes>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -1453,6 +1463,16 @@ void IMAPFolder::processStatusUpdate(const IMAPParser::response* resp)
|
|||||||
else if ((*it)->response_data() && (*it)->response_data()->mailbox_data())
|
else if ((*it)->response_data() && (*it)->response_data()->mailbox_data())
|
||||||
{
|
{
|
||||||
m_status->updateFromResponse((*it)->response_data()->mailbox_data());
|
m_status->updateFromResponse((*it)->response_data()->mailbox_data());
|
||||||
|
|
||||||
|
// Update folder attributes, if available
|
||||||
|
if ((*it)->response_data()->mailbox_data()->type() == IMAPParser::mailbox_data::LIST)
|
||||||
|
{
|
||||||
|
folderAttributes attribs;
|
||||||
|
IMAPUtils::mailboxFlagsToFolderAttributes
|
||||||
|
(m_connection, (*it)->response_data()->mailbox_data()->mailbox_list()->mailbox_flag_list(), attribs);
|
||||||
|
|
||||||
|
m_attribs = make_shared <folderAttributes>(attribs);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else if ((*it)->response_data() && (*it)->response_data()->message_data())
|
else if ((*it)->response_data() && (*it)->response_data()->message_data())
|
||||||
{
|
{
|
||||||
|
@ -66,22 +66,20 @@ private:
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
IMAPFolder(const folder::path& path, shared_ptr <IMAPStore> store, const int type = TYPE_UNDEFINED, const int flags = FLAG_UNDEFINED);
|
IMAPFolder(const folder::path& path, shared_ptr <IMAPStore> store, shared_ptr <folderAttributes> attribs);
|
||||||
|
|
||||||
~IMAPFolder();
|
~IMAPFolder();
|
||||||
|
|
||||||
int getMode() const;
|
int getMode() const;
|
||||||
|
|
||||||
int getType();
|
const folderAttributes getAttributes();
|
||||||
|
|
||||||
int getFlags();
|
|
||||||
|
|
||||||
const folder::path::component getName() const;
|
const folder::path::component getName() const;
|
||||||
const folder::path getFullPath() const;
|
const folder::path getFullPath() const;
|
||||||
|
|
||||||
void open(const int mode, bool failIfModeIsNotAvailable = false);
|
void open(const int mode, bool failIfModeIsNotAvailable = false);
|
||||||
void close(const bool expunge);
|
void close(const bool expunge);
|
||||||
void create(const int type);
|
void create(const folderAttributes& attribs);
|
||||||
|
|
||||||
bool exists();
|
bool exists();
|
||||||
|
|
||||||
@ -195,8 +193,7 @@ private:
|
|||||||
int m_mode;
|
int m_mode;
|
||||||
bool m_open;
|
bool m_open;
|
||||||
|
|
||||||
int m_type;
|
shared_ptr <folderAttributes> m_attribs;
|
||||||
int m_flags;
|
|
||||||
|
|
||||||
shared_ptr <IMAPFolderStatus> m_status;
|
shared_ptr <IMAPFolderStatus> m_status;
|
||||||
|
|
||||||
|
@ -1803,23 +1803,92 @@ public:
|
|||||||
const string name = utility::stringUtils::toLower(at->value());
|
const string name = utility::stringUtils::toLower(at->value());
|
||||||
delete (at);
|
delete (at);
|
||||||
|
|
||||||
if (name == "marked")
|
m_type = UNKNOWN; // default
|
||||||
m_type = MARKED;
|
|
||||||
else if (name == "noinferiors")
|
switch (name[0])
|
||||||
m_type = NOINFERIORS;
|
|
||||||
else if (name == "noselect")
|
|
||||||
m_type = NOSELECT;
|
|
||||||
else if (name == "unmarked")
|
|
||||||
m_type = UNMARKED;
|
|
||||||
else if (name == "haschildren")
|
|
||||||
m_type = HASCHILDREN;
|
|
||||||
else if (name == "hasnochildren")
|
|
||||||
m_type = HASNOCHILDREN;
|
|
||||||
else
|
|
||||||
{
|
{
|
||||||
m_type = UNKNOWN;
|
case 'a':
|
||||||
m_name = "\\" + name;
|
|
||||||
|
if (name == "all")
|
||||||
|
m_type = SPECIALUSE_ALL;
|
||||||
|
else if (name == "archive")
|
||||||
|
m_type = SPECIALUSE_ARCHIVE;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'd':
|
||||||
|
|
||||||
|
if (name == "drafts")
|
||||||
|
m_type = SPECIALUSE_DRAFTS;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'f':
|
||||||
|
|
||||||
|
if (name == "flagged")
|
||||||
|
m_type = SPECIALUSE_FLAGGED;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'h':
|
||||||
|
|
||||||
|
if (name == "haschildren")
|
||||||
|
m_type = HASCHILDREN;
|
||||||
|
else if (name == "hasnochildren")
|
||||||
|
m_type = HASNOCHILDREN;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'i':
|
||||||
|
|
||||||
|
if (name == "important")
|
||||||
|
m_type = SPECIALUSE_IMPORTANT;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'j':
|
||||||
|
|
||||||
|
if (name == "junk")
|
||||||
|
m_type = SPECIALUSE_JUNK;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'm':
|
||||||
|
|
||||||
|
if (name == "marked")
|
||||||
|
m_type = MARKED;
|
||||||
|
|
||||||
|
case 'n':
|
||||||
|
|
||||||
|
if (name == "noinferiors")
|
||||||
|
m_type = NOINFERIORS;
|
||||||
|
else if (name == "noselect")
|
||||||
|
m_type = NOSELECT;
|
||||||
|
|
||||||
|
case 's':
|
||||||
|
|
||||||
|
if (name == "sent")
|
||||||
|
m_type = SPECIALUSE_SENT;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 't':
|
||||||
|
|
||||||
|
if (name == "trash")
|
||||||
|
m_type = SPECIALUSE_TRASH;
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 'u':
|
||||||
|
|
||||||
|
if (name == "unmarked")
|
||||||
|
m_type = UNMARKED;
|
||||||
|
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (m_type == UNKNOWN)
|
||||||
|
m_name = "\\" + name;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -1841,6 +1910,16 @@ public:
|
|||||||
HASCHILDREN,
|
HASCHILDREN,
|
||||||
HASNOCHILDREN,
|
HASNOCHILDREN,
|
||||||
|
|
||||||
|
// RFC-6154 - Special-Use Mailboxes
|
||||||
|
SPECIALUSE_ALL,
|
||||||
|
SPECIALUSE_ARCHIVE,
|
||||||
|
SPECIALUSE_DRAFTS,
|
||||||
|
SPECIALUSE_FLAGGED,
|
||||||
|
SPECIALUSE_JUNK,
|
||||||
|
SPECIALUSE_SENT,
|
||||||
|
SPECIALUSE_TRASH,
|
||||||
|
SPECIALUSE_IMPORTANT, // draft
|
||||||
|
|
||||||
// Standard mailbox flags
|
// Standard mailbox flags
|
||||||
UNKNOWN,
|
UNKNOWN,
|
||||||
MARKED,
|
MARKED,
|
||||||
|
@ -76,7 +76,8 @@ shared_ptr <folder> IMAPStore::getRootFolder()
|
|||||||
|
|
||||||
return make_shared <IMAPFolder>
|
return make_shared <IMAPFolder>
|
||||||
(folder::path(),
|
(folder::path(),
|
||||||
dynamicCast <IMAPStore>(shared_from_this()));
|
dynamicCast <IMAPStore>(shared_from_this()),
|
||||||
|
shared_ptr <folderAttributes>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -87,7 +88,8 @@ shared_ptr <folder> IMAPStore::getDefaultFolder()
|
|||||||
|
|
||||||
return make_shared <IMAPFolder>
|
return make_shared <IMAPFolder>
|
||||||
(folder::path::component("INBOX"),
|
(folder::path::component("INBOX"),
|
||||||
dynamicCast <IMAPStore>(shared_from_this()));
|
dynamicCast <IMAPStore>(shared_from_this()),
|
||||||
|
shared_ptr <folderAttributes>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -97,7 +99,9 @@ shared_ptr <folder> IMAPStore::getFolder(const folder::path& path)
|
|||||||
throw exceptions::illegal_state("Not connected");
|
throw exceptions::illegal_state("Not connected");
|
||||||
|
|
||||||
return make_shared <IMAPFolder>
|
return make_shared <IMAPFolder>
|
||||||
(path, dynamicCast <IMAPStore>(shared_from_this()));
|
(path,
|
||||||
|
dynamicCast <IMAPStore>(shared_from_this()),
|
||||||
|
shared_ptr <folderAttributes>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -366,52 +366,89 @@ const folder::path::component IMAPUtils::fromModifiedUTF7(const string& text)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int IMAPUtils::folderTypeFromFlags(const IMAPParser::mailbox_flag_list* list)
|
// static
|
||||||
|
void IMAPUtils::mailboxFlagsToFolderAttributes
|
||||||
|
(shared_ptr <const IMAPConnection> cnt, const IMAPParser::mailbox_flag_list* list,
|
||||||
|
folderAttributes& attribs)
|
||||||
{
|
{
|
||||||
// Get folder type
|
int specialUse = folderAttributes::SPECIALUSE_NONE;
|
||||||
int type = folder::TYPE_CONTAINS_MESSAGES | folder::TYPE_CONTAINS_FOLDERS;
|
int type = folderAttributes::TYPE_CONTAINS_MESSAGES | folderAttributes::TYPE_CONTAINS_FOLDERS;
|
||||||
const std::vector <IMAPParser::mailbox_flag*>& flags = list->flags();
|
int flags = 0;
|
||||||
|
|
||||||
for (std::vector <IMAPParser::mailbox_flag*>::const_iterator it = flags.begin() ;
|
|
||||||
it != flags.end() ; ++it)
|
|
||||||
{
|
|
||||||
if ((*it)->type() == IMAPParser::mailbox_flag::NOSELECT)
|
|
||||||
type &= ~folder::TYPE_CONTAINS_MESSAGES;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (type & folder::TYPE_CONTAINS_MESSAGES)
|
|
||||||
type &= ~folder::TYPE_CONTAINS_FOLDERS;
|
|
||||||
|
|
||||||
return (type);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int IMAPUtils::folderFlagsFromFlags
|
|
||||||
(shared_ptr <const IMAPConnection> cnt, const IMAPParser::mailbox_flag_list* list)
|
|
||||||
{
|
|
||||||
int folderFlags = 0;
|
|
||||||
|
|
||||||
// If CHILDREN extension (RFC-3348) is not supported, assume folder has children
|
// If CHILDREN extension (RFC-3348) is not supported, assume folder has children
|
||||||
// as we have no hint about it
|
// as we have no hint about it
|
||||||
if (!cnt->hasCapability("CHILDREN"))
|
if (!cnt->hasCapability("CHILDREN"))
|
||||||
folderFlags |= folder::FLAG_HAS_CHILDREN;
|
flags |= folderAttributes::FLAG_HAS_CHILDREN;
|
||||||
|
|
||||||
const std::vector <IMAPParser::mailbox_flag*>& flags = list->flags();
|
const std::vector <IMAPParser::mailbox_flag*>& mailboxFlags = list->flags();
|
||||||
|
|
||||||
for (std::vector <IMAPParser::mailbox_flag*>::const_iterator it = flags.begin() ;
|
for (std::vector <IMAPParser::mailbox_flag*>::const_iterator it = mailboxFlags.begin() ;
|
||||||
it != flags.end() ; ++it)
|
it != mailboxFlags.end() ; ++it)
|
||||||
{
|
{
|
||||||
if ((*it)->type() == IMAPParser::mailbox_flag::NOSELECT)
|
switch ((*it)->type())
|
||||||
folderFlags |= folder::FLAG_NO_OPEN;
|
{
|
||||||
else if ((*it)->type() == IMAPParser::mailbox_flag::NOINFERIORS)
|
case IMAPParser::mailbox_flag::NOSELECT:
|
||||||
folderFlags &= ~folder::FLAG_HAS_CHILDREN;
|
|
||||||
else if ((*it)->type() == IMAPParser::mailbox_flag::HASNOCHILDREN)
|
type &= ~folderAttributes::TYPE_CONTAINS_MESSAGES;
|
||||||
folderFlags &= ~folder::FLAG_HAS_CHILDREN;
|
flags |= folderAttributes::FLAG_NO_OPEN;
|
||||||
else if ((*it)->type() == IMAPParser::mailbox_flag::HASCHILDREN)
|
break;
|
||||||
folderFlags |= folder::FLAG_HAS_CHILDREN;
|
|
||||||
|
case IMAPParser::mailbox_flag::NOINFERIORS:
|
||||||
|
case IMAPParser::mailbox_flag::HASNOCHILDREN:
|
||||||
|
|
||||||
|
flags &= ~folderAttributes::FLAG_HAS_CHILDREN;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::HASCHILDREN:
|
||||||
|
|
||||||
|
flags |= folderAttributes::FLAG_HAS_CHILDREN;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_ALL:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_ALL;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_ARCHIVE:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_ARCHIVE;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_DRAFTS:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_DRAFTS;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_FLAGGED:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_FLAGGED;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_JUNK:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_JUNK;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_SENT:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_SENT;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_TRASH:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_TRASH;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case IMAPParser::mailbox_flag::SPECIALUSE_IMPORTANT:
|
||||||
|
|
||||||
|
specialUse = folderAttributes::SPECIALUSE_IMPORTANT;
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return (folderFlags);
|
attribs.setSpecialUse(specialUse);
|
||||||
|
attribs.setType(type);
|
||||||
|
attribs.setFlags(flags);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -66,10 +66,16 @@ public:
|
|||||||
*/
|
*/
|
||||||
static const string quoteString(const string& text);
|
static const string quoteString(const string& text);
|
||||||
|
|
||||||
static int folderTypeFromFlags(const IMAPParser::mailbox_flag_list* list);
|
/** Parse mailbox flags and fill in folder attributes.
|
||||||
static int folderFlagsFromFlags
|
*
|
||||||
|
* @param cnt reference to current IMAP connection (for testing capabilities)
|
||||||
|
* @param list list of mailbox flags
|
||||||
|
* @param attribs reference to an object holding folder attributes
|
||||||
|
*/
|
||||||
|
static void mailboxFlagsToFolderAttributes
|
||||||
(shared_ptr <const IMAPConnection> cnt,
|
(shared_ptr <const IMAPConnection> cnt,
|
||||||
const IMAPParser::mailbox_flag_list* list);
|
const IMAPParser::mailbox_flag_list* list,
|
||||||
|
folderAttributes& attribs);
|
||||||
|
|
||||||
static int messageFlagsFromFlags(const IMAPParser::flag_list* list);
|
static int messageFlagsFromFlags(const IMAPParser::flag_list* list);
|
||||||
|
|
||||||
|
@ -91,23 +91,19 @@ int maildirFolder::getMode() const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int maildirFolder::getType()
|
const folderAttributes maildirFolder::getAttributes()
|
||||||
{
|
{
|
||||||
|
folderAttributes attribs;
|
||||||
|
|
||||||
if (m_path.isEmpty())
|
if (m_path.isEmpty())
|
||||||
return (TYPE_CONTAINS_FOLDERS);
|
attribs.setType(folderAttributes::TYPE_CONTAINS_FOLDERS);
|
||||||
else
|
else
|
||||||
return (TYPE_CONTAINS_FOLDERS | TYPE_CONTAINS_MESSAGES);
|
attribs.setType(folderAttributes::TYPE_CONTAINS_FOLDERS | folderAttributes::TYPE_CONTAINS_MESSAGES);
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int maildirFolder::getFlags()
|
|
||||||
{
|
|
||||||
int flags = 0;
|
|
||||||
|
|
||||||
if (m_store.lock()->getFormat()->folderHasSubfolders(m_path))
|
if (m_store.lock()->getFormat()->folderHasSubfolders(m_path))
|
||||||
flags |= FLAG_HAS_CHILDREN; // Contains at least one sub-folder
|
attribs.setFlags(folderAttributes::FLAG_HAS_CHILDREN); // contains at least one sub-folder
|
||||||
|
|
||||||
return (flags);
|
return attribs;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -189,7 +185,7 @@ void maildirFolder::unregisterMessage(maildirMessage* msg)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void maildirFolder::create(const int /* type */)
|
void maildirFolder::create(const folderAttributes& /* attribs */)
|
||||||
{
|
{
|
||||||
shared_ptr <maildirStore> store = m_store.lock();
|
shared_ptr <maildirStore> store = m_store.lock();
|
||||||
|
|
||||||
|
@ -71,16 +71,14 @@ public:
|
|||||||
|
|
||||||
int getMode() const;
|
int getMode() const;
|
||||||
|
|
||||||
int getType();
|
const folderAttributes getAttributes();
|
||||||
|
|
||||||
int getFlags();
|
|
||||||
|
|
||||||
const folder::path::component getName() const;
|
const folder::path::component getName() const;
|
||||||
const folder::path getFullPath() const;
|
const folder::path getFullPath() const;
|
||||||
|
|
||||||
void open(const int mode, bool failIfModeIsNotAvailable = false);
|
void open(const int mode, bool failIfModeIsNotAvailable = false);
|
||||||
void close(const bool expunge);
|
void close(const bool expunge);
|
||||||
void create(const int type);
|
void create(const folderAttributes& attribs);
|
||||||
|
|
||||||
bool exists();
|
bool exists();
|
||||||
|
|
||||||
|
@ -81,23 +81,23 @@ int POP3Folder::getMode() const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int POP3Folder::getType()
|
const folderAttributes POP3Folder::getAttributes()
|
||||||
{
|
{
|
||||||
if (!isOpen())
|
if (!isOpen())
|
||||||
throw exceptions::illegal_state("Folder not open");
|
throw exceptions::illegal_state("Folder not open");
|
||||||
|
|
||||||
|
folderAttributes attribs;
|
||||||
|
|
||||||
if (m_path.isEmpty())
|
if (m_path.isEmpty())
|
||||||
return (TYPE_CONTAINS_FOLDERS);
|
attribs.setType(folderAttributes::TYPE_CONTAINS_FOLDERS);
|
||||||
else if (m_path.getSize() == 1 && m_path[0].getBuffer() == "INBOX")
|
else if (m_path.getSize() == 1 && m_path[0].getBuffer() == "INBOX")
|
||||||
return (TYPE_CONTAINS_MESSAGES);
|
attribs.setType(folderAttributes::TYPE_CONTAINS_MESSAGES);
|
||||||
else
|
else
|
||||||
throw exceptions::folder_not_found();
|
throw exceptions::folder_not_found();
|
||||||
}
|
|
||||||
|
|
||||||
|
attribs.setFlags(0);
|
||||||
|
|
||||||
int POP3Folder::getFlags()
|
return attribs;
|
||||||
{
|
|
||||||
return (0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -186,7 +186,7 @@ void POP3Folder::onClose()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void POP3Folder::create(const int /* type */)
|
void POP3Folder::create(const folderAttributes& /* attribs */)
|
||||||
{
|
{
|
||||||
throw exceptions::operation_not_supported();
|
throw exceptions::operation_not_supported();
|
||||||
}
|
}
|
||||||
|
@ -68,16 +68,14 @@ public:
|
|||||||
|
|
||||||
int getMode() const;
|
int getMode() const;
|
||||||
|
|
||||||
int getType();
|
const folderAttributes getAttributes();
|
||||||
|
|
||||||
int getFlags();
|
|
||||||
|
|
||||||
const folder::path::component getName() const;
|
const folder::path::component getName() const;
|
||||||
const folder::path getFullPath() const;
|
const folder::path getFullPath() const;
|
||||||
|
|
||||||
void open(const int mode, bool failIfModeIsNotAvailable = false);
|
void open(const int mode, bool failIfModeIsNotAvailable = false);
|
||||||
void close(const bool expunge);
|
void close(const bool expunge);
|
||||||
void create(const int type);
|
void create(const folderAttributes& attribs);
|
||||||
|
|
||||||
bool exists();
|
bool exists();
|
||||||
|
|
||||||
|
137
tests/net/folderAttributesTest.cpp
Normal file
137
tests/net/folderAttributesTest.cpp
Normal file
@ -0,0 +1,137 @@
|
|||||||
|
//
|
||||||
|
// VMime library (http://www.vmime.org)
|
||||||
|
// Copyright (C) 2002-2014 Vincent Richard <vincent@vmime.org>
|
||||||
|
//
|
||||||
|
// 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 3 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; if not, write to the Free Software Foundation, Inc.,
|
||||||
|
// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||||
|
//
|
||||||
|
// Linking this library statically or dynamically with other modules is making
|
||||||
|
// a combined work based on this library. Thus, the terms and conditions of
|
||||||
|
// the GNU General Public License cover the whole combination.
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "tests/testUtils.hpp"
|
||||||
|
|
||||||
|
#include "vmime/net/folderAttributes.hpp"
|
||||||
|
|
||||||
|
|
||||||
|
VMIME_TEST_SUITE_BEGIN(folderAttributesTest)
|
||||||
|
|
||||||
|
VMIME_TEST_LIST_BEGIN
|
||||||
|
VMIME_TEST(testConstruct)
|
||||||
|
VMIME_TEST(testConstructCopy)
|
||||||
|
VMIME_TEST(testSetType)
|
||||||
|
VMIME_TEST(testSetFlags)
|
||||||
|
VMIME_TEST(testHasFlag)
|
||||||
|
VMIME_TEST(testSetUserFlags)
|
||||||
|
VMIME_TEST(testHasUserFlag)
|
||||||
|
VMIME_TEST(testSetSpecialUse)
|
||||||
|
VMIME_TEST_LIST_END
|
||||||
|
|
||||||
|
|
||||||
|
void testConstruct()
|
||||||
|
{
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
|
||||||
|
// Default values
|
||||||
|
VASSERT_EQ("type", vmime::net::folderAttributes::TYPE_CONTAINS_FOLDERS
|
||||||
|
| vmime::net::folderAttributes::TYPE_CONTAINS_MESSAGES, attr.getType());
|
||||||
|
VASSERT_EQ("flags", 0, attr.getFlags());
|
||||||
|
VASSERT_EQ("user-flags", 0, attr.getUserFlags().size());
|
||||||
|
VASSERT_EQ("special-use", vmime::net::folderAttributes::SPECIALUSE_NONE, attr.getSpecialUse());
|
||||||
|
}
|
||||||
|
|
||||||
|
void testConstructCopy()
|
||||||
|
{
|
||||||
|
std::vector <vmime::string> userFlags;
|
||||||
|
userFlags.push_back("\\XMyFlag1");
|
||||||
|
userFlags.push_back("\\XMyFlag2");
|
||||||
|
userFlags.push_back("\\XMyFlag3");
|
||||||
|
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
|
||||||
|
attr.setFlags(vmime::net::folderAttributes::FLAG_HAS_CHILDREN);
|
||||||
|
attr.setUserFlags(userFlags);
|
||||||
|
|
||||||
|
vmime::net::folderAttributes attr2(attr);
|
||||||
|
|
||||||
|
VASSERT("flags", attr2.getFlags() == attr.getFlags());
|
||||||
|
VASSERT("user-flags", attr2.getUserFlags() == attr.getUserFlags());
|
||||||
|
}
|
||||||
|
|
||||||
|
void testSetType()
|
||||||
|
{
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
attr.setType(vmime::net::folderAttributes::TYPE_CONTAINS_FOLDERS);
|
||||||
|
|
||||||
|
VASSERT_EQ("eq", vmime::net::folderAttributes::TYPE_CONTAINS_FOLDERS, attr.getType());
|
||||||
|
}
|
||||||
|
|
||||||
|
void testSetFlags()
|
||||||
|
{
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
attr.setFlags(vmime::net::folderAttributes::FLAG_HAS_CHILDREN);
|
||||||
|
|
||||||
|
VASSERT_EQ("eq", vmime::net::folderAttributes::FLAG_HAS_CHILDREN, attr.getFlags());
|
||||||
|
}
|
||||||
|
|
||||||
|
void testHasFlag()
|
||||||
|
{
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
attr.setFlags(vmime::net::folderAttributes::FLAG_HAS_CHILDREN);
|
||||||
|
|
||||||
|
VASSERT("has", attr.hasFlag(vmime::net::folderAttributes::FLAG_HAS_CHILDREN));
|
||||||
|
VASSERT("has-not", !attr.hasFlag(vmime::net::folderAttributes::FLAG_NO_OPEN));
|
||||||
|
}
|
||||||
|
|
||||||
|
void testSetUserFlags()
|
||||||
|
{
|
||||||
|
std::vector <vmime::string> userFlags;
|
||||||
|
userFlags.push_back("\\XMyFlag1");
|
||||||
|
userFlags.push_back("\\XMyFlag2");
|
||||||
|
userFlags.push_back("\\XMyFlag3");
|
||||||
|
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
attr.setUserFlags(userFlags);
|
||||||
|
|
||||||
|
VASSERT("eq", attr.getUserFlags() == userFlags);
|
||||||
|
}
|
||||||
|
|
||||||
|
void testHasUserFlag()
|
||||||
|
{
|
||||||
|
std::vector <vmime::string> userFlags;
|
||||||
|
userFlags.push_back("\\XMyFlag1");
|
||||||
|
userFlags.push_back("\\XMyFlag2");
|
||||||
|
userFlags.push_back("\\XMyFlag3");
|
||||||
|
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
attr.setUserFlags(userFlags);
|
||||||
|
|
||||||
|
VASSERT("has", attr.hasUserFlag("\\XMyFlag1"));
|
||||||
|
VASSERT("has-casesensitive", !attr.hasUserFlag("\\xmyflag1"));
|
||||||
|
VASSERT("has-not", !attr.hasUserFlag("\\XMyFlag4"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void testSetSpecialUse()
|
||||||
|
{
|
||||||
|
const int use = vmime::net::folderAttributes::SPECIALUSE_JUNK
|
||||||
|
| vmime::net::folderAttributes::SPECIALUSE_TRASH;
|
||||||
|
|
||||||
|
vmime::net::folderAttributes attr;
|
||||||
|
attr.setSpecialUse(use);
|
||||||
|
|
||||||
|
VASSERT_EQ("eq", use, attr.getSpecialUse());
|
||||||
|
}
|
||||||
|
|
||||||
|
VMIME_TEST_SUITE_END
|
@ -456,8 +456,10 @@ public:
|
|||||||
|
|
||||||
VASSERT("Before", !store->getFolder(fpath() / "Folder" / "NewFolder")->exists());
|
VASSERT("Before", !store->getFolder(fpath() / "Folder" / "NewFolder")->exists());
|
||||||
|
|
||||||
VASSERT_NO_THROW("Creation", store->getFolder(fpath() / "Folder" / "NewFolder")->
|
vmime::net::folderAttributes attribs;
|
||||||
create(vmime::net::folder::TYPE_CONTAINS_MESSAGES));
|
attribs.setType(vmime::net::folderAttributes::TYPE_CONTAINS_MESSAGES);
|
||||||
|
|
||||||
|
VASSERT_NO_THROW("Creation", store->getFolder(fpath() / "Folder" / "NewFolder")->create(attribs));
|
||||||
|
|
||||||
VASSERT("After", store->getFolder(fpath() / "Folder" / "NewFolder")->exists());
|
VASSERT("After", store->getFolder(fpath() / "Folder" / "NewFolder")->exists());
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user