aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core/rfc822
diff options
context:
space:
mode:
authorGravatar Hoà V. DINH <dinh.viet.hoa@gmail.com>2014-08-02 17:51:40 -0700
committerGravatar Hoà V. DINH <dinh.viet.hoa@gmail.com>2014-08-02 17:51:40 -0700
commit3db6e0e46595a617468cf239eae9fe1978e60651 (patch)
tree6c97ad9f4ac89b24c7cc65aea356e8aff178c120 /src/core/rfc822
parent085e89548ed3acc377b21e82bf822dad9836839e (diff)
parentc1efc1d44b0a315b17701aed28c7de096b413337 (diff)
Merge pull request #814 from foxinushka/feature/attachment-extra-parameters
Added extra parameters to attachment
Diffstat (limited to 'src/core/rfc822')
-rw-r--r--src/core/rfc822/MCAttachment.cc73
-rw-r--r--src/core/rfc822/MCAttachment.h8
-rw-r--r--src/core/rfc822/MCMessageBuilder.cc81
3 files changed, 139 insertions, 23 deletions
diff --git a/src/core/rfc822/MCAttachment.cc b/src/core/rfc822/MCAttachment.cc
index d016ad0e..172881cb 100644
--- a/src/core/rfc822/MCAttachment.cc
+++ b/src/core/rfc822/MCAttachment.cc
@@ -211,6 +211,8 @@ Attachment * Attachment::attachmentWithText(String * text)
void Attachment::init()
{
mData = NULL;
+ mContentTypeParameters = NULL;
+ mlcContentTypeParameters = NULL;
setMimeType(MCSTR("application/octet-stream"));
}
@@ -223,11 +225,14 @@ Attachment::Attachment(Attachment * other) : AbstractPart(other)
{
init();
MC_SAFE_REPLACE_RETAIN(Data, mData, other->mData);
+ setContentTypeParameters(other->mContentTypeParameters);
}
Attachment::~Attachment()
{
MC_SAFE_RELEASE(mData);
+ MC_SAFE_RELEASE(mContentTypeParameters);
+ MC_SAFE_RELEASE(mlcContentTypeParameters);
}
String * Attachment::description()
@@ -256,6 +261,11 @@ String * Attachment::description()
else {
result->appendUTF8Format("no data\n");
}
+ if (mContentTypeParameters != NULL) {
+ mc_foreachhashmapKeyAndValue(String, key, String, value, mContentTypeParameters) {
+ result->appendUTF8Format("%s: %s\n", key->UTF8Characters(), value->UTF8Characters());
+ }
+ }
result->appendUTF8Format(">");
return result;
@@ -286,6 +296,55 @@ String * Attachment::decodedString()
}
}
+void Attachment::setContentTypeParameters(HashMap * parameters)
+{
+ MC_SAFE_REPLACE_COPY(HashMap, mContentTypeParameters, parameters);
+ MC_SAFE_RELEASE(mlcContentTypeParameters);
+ if (mContentTypeParameters != NULL) {
+ mlcContentTypeParameters = new HashMap();
+ mc_foreachhashmapKeyAndValue(String, key, String, value, mContentTypeParameters) {
+ mlcContentTypeParameters->setObjectForKey(key->lowercaseString(), value);
+ }
+ }
+}
+
+Array * Attachment::allContentTypeParametersNames()
+{
+ if (mContentTypeParameters == NULL)
+ return Array::array();
+ return mContentTypeParameters->allKeys();
+}
+
+void Attachment::setContentTypeParameter(String * name, String * object)
+{
+ if (mContentTypeParameters == NULL) {
+ mContentTypeParameters = new HashMap();
+ }
+ if (mlcContentTypeParameters == NULL) {
+ mlcContentTypeParameters = new HashMap();
+ }
+ if (object == NULL) {
+ removeContentTypeParameter(name);
+ return;
+ }
+ mContentTypeParameters->setObjectForKey(name, object);
+ mlcContentTypeParameters->setObjectForKey(name->lowercaseString(), object);
+}
+
+void Attachment::removeContentTypeParameter(String * name)
+{
+ if (mContentTypeParameters == NULL)
+ return;
+ mContentTypeParameters->removeObjectForKey(name);
+ mlcContentTypeParameters->removeObjectForKey(name);
+}
+
+String * Attachment::contentTypeParameterValueForName(String * name)
+{
+ if (mlcContentTypeParameters == NULL)
+ return NULL;
+ return (String *) mlcContentTypeParameters->objectForKey(name->lowercaseString());
+}
AbstractPart * Attachment::attachmentsWithMIME(struct mailmime * mime)
{
@@ -503,6 +562,7 @@ Attachment * Attachment::attachmentWithSingleMIME(struct mailmime * mime)
char * description;
char * loc;
Encoding encoding;
+ clist * ct_parameters;
MCAssert(mime->mm_type == MAILMIME_SINGLE);
@@ -531,6 +591,7 @@ Attachment * Attachment::attachmentWithSingleMIME(struct mailmime * mime)
content_id = single_fields.fld_id;
description = single_fields.fld_description;
loc = single_fields.fld_location;
+ ct_parameters = single_fields.fld_content->ct_parameters;
if (filename != NULL) {
result->setFilename(String::stringByDecodingMIMEHeaderValue(filename));
@@ -551,6 +612,18 @@ Attachment * Attachment::attachmentWithSingleMIME(struct mailmime * mime)
result->setContentLocation(String::stringWithUTF8Characters(loc));
}
+ if (ct_parameters != NULL) {
+ clistiter * iter = clist_begin(ct_parameters);
+ struct mailmime_parameter * param;
+ while (iter != NULL) {
+ param = (struct mailmime_parameter *) clist_content(iter);
+ if (param != NULL) {
+ result->setContentTypeParameter(String::stringWithUTF8Characters(param->pa_name), String::stringWithUTF8Characters(param->pa_value));
+ }
+ iter = clist_next(iter);
+ }
+ }
+
if (single_fields.fld_disposition != NULL) {
if (single_fields.fld_disposition->dsp_type != NULL) {
if (single_fields.fld_disposition->dsp_type->dsp_type == MAILMIME_DISPOSITION_TYPE_INLINE) {
diff --git a/src/core/rfc822/MCAttachment.h b/src/core/rfc822/MCAttachment.h
index 7dd15b89..069688f2 100644
--- a/src/core/rfc822/MCAttachment.h
+++ b/src/core/rfc822/MCAttachment.h
@@ -29,6 +29,11 @@ namespace mailcore {
virtual Data * data();
virtual String * decodedString();
+ virtual void setContentTypeParameter(String * name, String * value);
+ virtual void removeContentTypeParameter(String * name);
+ virtual String * contentTypeParameterValueForName(String *name);
+ virtual Array * allContentTypeParametersNames();
+
public: // subclass behavior
Attachment(Attachment * other);
virtual String * description();
@@ -39,6 +44,8 @@ namespace mailcore {
private:
Data * mData;
+ HashMap * mContentTypeParameters;
+ HashMap * mlcContentTypeParameters;
void init();
static void fillMultipartSubAttachments(AbstractMultipart * multipart, struct mailmime * mime);
static AbstractPart * attachmentsWithMIMEWithMain(struct mailmime * mime, bool isMain);
@@ -46,6 +53,7 @@ namespace mailcore {
static MessagePart * attachmentWithMessageMIME(struct mailmime * mime);
static Encoding encodingForMIMEEncoding(struct mailmime_mechanism * mechanism, int defaultMimeEncoding);
static HashMap * readMimeTypesFile(String * filename);
+ void setContentTypeParameters(HashMap * parameters);
};
}
diff --git a/src/core/rfc822/MCMessageBuilder.cc b/src/core/rfc822/MCMessageBuilder.cc
index cd87009e..3e63ce4a 100644
--- a/src/core/rfc822/MCMessageBuilder.cc
+++ b/src/core/rfc822/MCMessageBuilder.cc
@@ -134,7 +134,7 @@ err:
static struct mailmime * get_text_part(const char * mime_type, const char * charset, const char * content_id,
const char * description,
- const char * text, size_t length, int encoding_type)
+ const char * text, size_t length, int encoding_type, clist * contentTypeParameters)
{
struct mailmime_fields * mime_fields;
struct mailmime * mime;
@@ -165,6 +165,10 @@ static struct mailmime * get_text_part(const char * mime_type, const char * char
param = mailmime_param_new_with_data((char *) "charset", (char *) charset);
}
clist_append(content->ct_parameters, param);
+ if (contentTypeParameters != NULL) {
+ clist_concat(content->ct_parameters, contentTypeParameters);
+ }
+
mime = part_new_empty(content, mime_fields, NULL, 1);
mailmime_set_body_text(mime, (char *) text, length);
@@ -173,7 +177,7 @@ static struct mailmime * get_text_part(const char * mime_type, const char * char
static struct mailmime * get_plain_text_part(const char * mime_type, const char * charset, const char * content_id,
const char * description,
- const char * text, size_t length)
+ const char * text, size_t length, clist * contentTypeParameters)
{
bool needsQuotedPrintable;
int mechanism;
@@ -189,20 +193,20 @@ static struct mailmime * get_plain_text_part(const char * mime_type, const char
if (needsQuotedPrintable) {
mechanism = MAILMIME_MECHANISM_QUOTED_PRINTABLE;
}
- return get_text_part(mime_type, charset, content_id, description, text, length, mechanism);
+ return get_text_part(mime_type, charset, content_id, description, text, length, mechanism, contentTypeParameters);
}
static struct mailmime * get_other_text_part(const char * mime_type, const char * charset, const char * content_id,
const char * description,
- const char * text, size_t length)
+ const char * text, size_t length, clist * contentTypeParameters)
{
- return get_text_part(mime_type, charset, content_id, description, text, length, MAILMIME_MECHANISM_QUOTED_PRINTABLE);
+ return get_text_part(mime_type, charset, content_id, description, text, length, MAILMIME_MECHANISM_QUOTED_PRINTABLE, contentTypeParameters);
}
static struct mailmime * get_file_part(const char * filename, const char * mime_type, int is_inline,
const char * content_id,
const char * content_description,
- const char * text, size_t length)
+ const char * text, size_t length, clist * contentTypeParameters)
{
char * disposition_name;
int encoding_type;
@@ -238,6 +242,11 @@ static struct mailmime * get_file_part(const char * filename, const char * mime_
dup_content_description = strdup(content_description);
mime_fields = mailmime_fields_new_with_data(encoding,
dup_content_id, dup_content_description, disposition, NULL);
+
+ if (contentTypeParameters != NULL) {
+ clist_concat(content->ct_parameters, contentTypeParameters);
+ }
+
mime = part_new_empty(content, mime_fields, NULL, 1);
mailmime_set_body_text(mime, (char *) text, length);
@@ -246,6 +255,23 @@ static struct mailmime * get_file_part(const char * filename, const char * mime_
#define MIME_ENCODED_STR(str) (str != NULL ? str->encodedMIMEHeaderValue()->bytes() : NULL)
+static clist * content_type_parameters_from_attachment(Attachment * att)
+{
+ clist * contentTypeParameters = NULL;
+ struct mailmime_parameter * param;
+
+ mc_foreacharray(String, name, att->allContentTypeParametersNames()) {
+ if (contentTypeParameters == NULL) {
+ contentTypeParameters = clist_new();
+ }
+ String * value = att->contentTypeParameterValueForName(name);
+ param = mailmime_param_new_with_data((char *)name->UTF8Characters(), (char *)value->UTF8Characters());
+ clist_append(contentTypeParameters, param);
+ }
+
+ return contentTypeParameters;
+}
+
static struct mailmime * mime_from_attachment(Attachment * att)
{
struct mailmime * mime;
@@ -262,24 +288,33 @@ static struct mailmime * mime_from_attachment(Attachment * att)
if (r != MAILIMF_NO_ERROR)
return NULL;
}
- else if (att->isInlineAttachment() && att->mimeType()->lowercaseString()->isEqual(MCSTR("text/plain"))) {
- mime = get_plain_text_part(MCUTF8(att->mimeType()), MCUTF8(att->charset()),
- MCUTF8(att->contentID()),
- MIME_ENCODED_STR(att->contentDescription()),
- data->bytes(), data->length());
- }
- else if (att->isInlineAttachment() && att->mimeType()->lowercaseString()->hasPrefix(MCSTR("text/"))) {
- mime = get_other_text_part(MCUTF8(att->mimeType()), MCUTF8(att->charset()),
- MCUTF8(att->contentID()),
- MIME_ENCODED_STR(att->contentDescription()),
- data->bytes(), data->length());
- }
else {
- mime = get_file_part(MIME_ENCODED_STR(att->filename()),
- MCUTF8(att->mimeType()), att->isInlineAttachment(),
- MCUTF8(att->contentID()),
- MIME_ENCODED_STR(att->contentDescription()),
- data->bytes(), data->length());
+ clist * contentTypeParameters = content_type_parameters_from_attachment(att);
+ if (att->isInlineAttachment() && att->mimeType()->lowercaseString()->isEqual(MCSTR("text/plain"))) {
+ mime = get_plain_text_part(MCUTF8(att->mimeType()), MCUTF8(att->charset()),
+ MCUTF8(att->contentID()),
+ MIME_ENCODED_STR(att->contentDescription()),
+ data->bytes(), data->length(),
+ contentTypeParameters);
+ }
+ else if (att->isInlineAttachment() && att->mimeType()->lowercaseString()->hasPrefix(MCSTR("text/"))) {
+ mime = get_other_text_part(MCUTF8(att->mimeType()), MCUTF8(att->charset()),
+ MCUTF8(att->contentID()),
+ MIME_ENCODED_STR(att->contentDescription()),
+ data->bytes(), data->length(),
+ contentTypeParameters);
+ }
+ else {
+ mime = get_file_part(MIME_ENCODED_STR(att->filename()),
+ MCUTF8(att->mimeType()), att->isInlineAttachment(),
+ MCUTF8(att->contentID()),
+ MIME_ENCODED_STR(att->contentDescription()),
+ data->bytes(), data->length(),
+ contentTypeParameters);
+ }
+ if (contentTypeParameters != NULL) {
+ clist_free(contentTypeParameters);
+ }
}
return mime;
}