diff options
author | Vincent Richard <[email protected]> | 2004-10-21 15:05:47 +0000 |
---|---|---|
committer | Vincent Richard <[email protected]> | 2004-10-21 15:05:47 +0000 |
commit | 2949fb51f13e1236d5c161f02e1c2c8541100e9f (patch) | |
tree | 991edcf50483116ce83977a4d9e652de8c5328dc /src/header.cpp | |
parent | header class unit tests added (diff) | |
download | vmime-2949fb51f13e1236d5c161f02e1c2c8541100e9f.tar.gz vmime-2949fb51f13e1236d5c161f02e1c2c8541100e9f.zip |
Refactoring (see ChangeLog).
Diffstat (limited to 'src/header.cpp')
-rw-r--r-- | src/header.cpp | 290 |
1 files changed, 155 insertions, 135 deletions
diff --git a/src/header.cpp b/src/header.cpp index eb972de0..317189b8 100644 --- a/src/header.cpp +++ b/src/header.cpp @@ -32,6 +32,7 @@ header::header() header::~header() { + removeAllFields(); } @@ -59,7 +60,7 @@ void header::parse(const string& buffer, const string::size_type position, { string::size_type pos = position; - fields.clear(); + removeAllFields(); while (pos < end) { @@ -181,8 +182,8 @@ void header::parse(const string& buffer, const string::size_type position, } // Add a new field to list - fields.m_fields.push_back(headerFieldFactory::getInstance()-> - create(headerField::nameToType(name), name, contents)); + m_fields.push_back(headerFieldFactory::getInstance()-> + create(name, contents)); } } else @@ -220,8 +221,8 @@ void header::generate(utility::outputStream& os, const string::size_type maxLine const string::size_type /* curLinePos */, string::size_type* newLinePos) const { // Generate the fields - for (std::vector <headerField*>::const_iterator - it = fields.m_fields.begin() ; it != fields.m_fields.end() ; ++it) + for (std::vector <headerField*>::const_iterator it = m_fields.begin() ; + it != m_fields.end() ; ++it) { (*it)->generate(os, maxLineLength); os << CRLF; @@ -232,93 +233,91 @@ void header::generate(utility::outputStream& os, const string::size_type maxLine } -header& header::operator=(const header& h) +header* header::clone() const { - fields = h.fields; + header* hdr = new header(); - return (*this); -} + try + { + hdr->m_fields.reserve(m_fields.size()); + for (std::vector <headerField*>::const_iterator it = m_fields.begin() ; + it != m_fields.end() ; ++it) + { + hdr->m_fields.push_back((*it)->clone()); + } + } + catch (std::exception&) + { + free_container(hdr->m_fields); + delete (hdr); + throw; + } -////////////////////// -// Fields container // -////////////////////// + return (hdr); +} -header::fieldsContainer::fieldsContainer() +void header::copyFrom(const component& other) { -} + const header& h = dynamic_cast <const header&>(other); + std::vector <headerField*> fields; -header::fieldsContainer::~fieldsContainer() -{ - for (std::vector <headerField*>::iterator i = m_fields.begin() ; i != m_fields.end() ; ++i) - delete (*i); -} + try + { + fields.reserve(h.m_fields.size()); + for (std::vector <headerField*>::const_iterator it = h.m_fields.begin() ; + it != h.m_fields.end() ; ++it) + { + fields.push_back((*it)->clone()); + } -// Checks whether (at least) one field with this type/name exists -const bool header::fieldsContainer::has(const headerField::Types fieldType) const -{ - std::vector <headerField*>::const_iterator pos = m_fields.begin(); - const std::vector <headerField*>::const_iterator end = m_fields.end(); + free_container(m_fields); - for ( ; pos != end && (*pos)->type() != fieldType ; ++pos); + m_fields.resize(fields.size()); - return (pos != end); + std::copy(fields.begin(), fields.end(), m_fields.begin()); + } + catch (std::exception&) + { + free_container(fields); + throw; + } } -const bool header::fieldsContainer::has(const string& fieldName) const +header& header::operator=(const header& other) { - headerField::Types type = headerField::nameToType(fieldName); - if (type != headerField::Custom) return (has(type)); - - const string name = toLower(fieldName); - - std::vector <headerField*>::const_iterator pos = m_fields.begin(); - const std::vector <headerField*>::const_iterator end = m_fields.end(); - - for ( ; pos != end && toLower((*pos)->name()) != name ; ++pos); - - return (pos != end); + copyFrom(other); + return (*this); } -headerField& header::fieldsContainer::find(const headerField::Types fieldType) const +const bool header::hasField(const string& fieldName) const { - // Find the first field that matches the specified type + const string name = stringUtils::toLower(fieldName); + std::vector <headerField*>::const_iterator pos = m_fields.begin(); const std::vector <headerField*>::const_iterator end = m_fields.end(); - for ( ; pos != end && (*pos)->type() != fieldType ; ++pos); + for ( ; pos != end && stringUtils::toLower((*pos)->getName()) != name ; ++pos); - // No field with this type can be found - if (pos == end) - { - throw exceptions::no_such_field(); - } - // Else, return a reference to the existing field - else - { - return (**pos); - } + return (pos != end); } -headerField& header::fieldsContainer::find(const string& fieldName) const +headerField* header::findField(const string& fieldName) const { - headerField::Types type = headerField::nameToType(fieldName); - if (type != headerField::Custom) return (find(type)); - - const string name = toLower(fieldName); + const string name = stringUtils::toLower(fieldName); // Find the first field that matches the specified name std::vector <headerField*>::const_iterator pos = m_fields.begin(); const std::vector <headerField*>::const_iterator end = m_fields.end(); - for ( ; pos != end && toLower((*pos)->name()) != name ; ++pos); + for ( ; pos != end && stringUtils::toLower((*pos)->getName()) != name ; ++pos); // No field with this name can be found if (pos == end) @@ -328,13 +327,15 @@ headerField& header::fieldsContainer::find(const string& fieldName) const // Else, return a reference to the existing field else { - return (**pos); + return (*pos); } } -std::vector <headerField*> header::fieldsContainer::findAllByType(const headerField::Types fieldType) +std::vector <headerField*> header::findAllFields(const string& fieldName) { + const string name = stringUtils::toLower(fieldName); + std::vector <headerField*> result; std::vector <headerField*>::const_iterator pos = m_fields.begin(); @@ -343,7 +344,7 @@ std::vector <headerField*> header::fieldsContainer::findAllByType(const headerFi for ( ; pos != end ; ++pos) { // Add the header if it matches the specified type - if ((*pos)->type() == fieldType) + if (stringUtils::toLower((*pos)->getName()) == name) { result.push_back(*pos); } @@ -353,138 +354,157 @@ std::vector <headerField*> header::fieldsContainer::findAllByType(const headerFi } -std::vector <headerField*> header::fieldsContainer::findAllByName(const string& fieldName) +headerField* header::getField(const string& fieldName) { - const string name = toLower(fieldName); - - std::vector <headerField*> result; + const string name = stringUtils::toLower(fieldName); + // Find the first field that matches the specified name std::vector <headerField*>::const_iterator pos = m_fields.begin(); const std::vector <headerField*>::const_iterator end = m_fields.end(); - for ( ; pos != end ; ++pos) + for ( ; pos != end && stringUtils::toLower((*pos)->getName()) != name ; ++pos); + + // If no field with this name can be found, create a new one + if (pos == end) { - // Add the header if it matches the specified type - if (toLower((*pos)->name()) == name) + headerField* field = headerFieldFactory::getInstance()->create(fieldName); + + try { - result.push_back(*pos); + appendField(field); } + catch (std::exception&) + { + delete (field); + throw; + } + + // Return a reference to the new field + return (field); } + // Else, return a reference to the existing field + else + { + return (*pos); + } +} - return result; + +void header::appendField(headerField* field) +{ + m_fields.push_back(field); } -headerField& header::fieldsContainer::get(const headerField::Types fieldType) +void header::insertFieldBefore(headerField* beforeField, headerField* field) { - // Find the first field that matches the specified type - std::vector <headerField*>::const_iterator pos = m_fields.begin(); - const std::vector <headerField*>::const_iterator end = m_fields.end(); + const std::vector <headerField*>::iterator it = std::find + (m_fields.begin(), m_fields.end(), beforeField); - for ( ; pos != end && (*pos)->type() != fieldType ; ++pos); + if (it == m_fields.end()) + throw exceptions::no_such_field(); - // If no field with this type can be found, create a new one - if (pos == end) - { - headerField* field = headerFieldFactory::getInstance()->create(fieldType); - insertSorted(field); + m_fields.insert(it, field); +} - // Return a reference to the new field - return (*field); - } - // Else, return a reference to the existing field - else - { - return (**pos); - } + +void header::insertFieldBefore(const int pos, headerField* field) +{ + m_fields.insert(m_fields.begin() + pos, field); } -headerField& header::fieldsContainer::get(const string& fieldName) +void header::insertFieldAfter(headerField* afterField, headerField* field) { - headerField::Types type = headerField::nameToType(fieldName); - if (type != headerField::Custom) return (get(type)); + const std::vector <headerField*>::iterator it = std::find + (m_fields.begin(), m_fields.end(), afterField); - const string name = toLower(fieldName); + if (it == m_fields.end()) + throw exceptions::no_such_field(); - // Find the first field that matches the specified name - std::vector <headerField*>::const_iterator pos = m_fields.begin(); - const std::vector <headerField*>::const_iterator end = m_fields.end(); + m_fields.insert(it + 1, field); +} - for ( ; pos != end && toLower((*pos)->name()) != name ; ++pos); - // If no field with this name can be found, create a new one - if (pos == end) - { - headerField* field = headerFieldFactory::getInstance()->create(fieldName); - insertSorted(field); +void header::insertFieldAfter(const int pos, headerField* field) +{ + m_fields.insert(m_fields.begin() + pos + 1, field); +} - // Return a reference to the new field - return (*field); - } - // Else, return a reference to the existing field - else - { - return (**pos); - } + +void header::removeField(headerField* field) +{ + const std::vector <headerField*>::iterator it = std::find + (m_fields.begin(), m_fields.end(), field); + + if (it == m_fields.end()) + throw exceptions::no_such_field(); + + delete (*it); + + m_fields.erase(it); } -void header::fieldsContainer::insertSorted(headerField* field) +void header::removeField(const int pos) { - const headerField::Types type = field->type(); - std::vector <headerField*>::iterator i; + const std::vector <headerField*>::iterator it = m_fields.begin() + pos; - for (i = m_fields.begin() ; (i != m_fields.end()) && ((*i)->type() < type) ; ++i); + delete (*it); - m_fields.insert(i, field); + m_fields.erase(it); } -// Field insertion -void header::fieldsContainer::append(const headerField& field) +void header::removeAllFields() { - m_fields.push_back(field.clone()); + free_container(m_fields); } -void header::fieldsContainer::insert(const iterator it, const headerField& field) +const int header::getFieldCount() const { - m_fields.insert(it.m_iterator, field.clone()); + return (m_fields.size()); } -// Field removing -void header::fieldsContainer::remove(const iterator it) +const bool header::isEmpty() const { - delete (*it.m_iterator); - m_fields.erase(it.m_iterator); + return (m_fields.empty()); } -void header::fieldsContainer::clear() +headerField* header::getFieldAt(const int pos) { - for (std::vector <headerField*>::iterator it = m_fields.begin() ; it != m_fields.end() ; ++it) - delete (*it); + return (m_fields[pos]); +} + - m_fields.clear(); +const headerField* const header::getFieldAt(const int pos) const +{ + return (m_fields[pos]); } -header::fieldsContainer& header::fieldsContainer::operator=(const fieldsContainer& c) +const std::vector <const headerField*> header::getFieldList() const { - std::vector <headerField*> fields; + std::vector <const headerField*> list; - for (std::vector <headerField*>::const_iterator it = c.m_fields.begin() ; it != c.m_fields.end() ; ++it) - fields.push_back((*it)->clone()); + list.reserve(m_fields.size()); - for (std::vector <headerField*>::iterator it = m_fields.begin() ; it != m_fields.end() ; ++it) - delete (*it); + for (std::vector <headerField*>::const_iterator it = m_fields.begin() ; + it != m_fields.end() ; ++it) + { + list.push_back(*it); + } - m_fields.resize(fields.size()); - std::copy(fields.begin(), fields.end(), m_fields.begin()); + return (list); +} - return (*this); + +const std::vector <headerField*> header::getFieldList() +{ + return (m_fields); } |