diff --git a/src/chat/modifier/cpim-chat-message-modifier.cpp b/src/chat/modifier/cpim-chat-message-modifier.cpp index 04c73f9c1..39104a674 100644 --- a/src/chat/modifier/cpim-chat-message-modifier.cpp +++ b/src/chat/modifier/cpim-chat-message-modifier.cpp @@ -38,29 +38,30 @@ LINPHONE_BEGIN_NAMESPACE ChatMessageModifier::Result CpimChatMessageModifier::encode (const shared_ptr &message, int &errorCode) { Cpim::Message cpimMessage; - Cpim::FromHeader cpimFromHeader(cpimAddressUri(message->getFromAddress()), cpimAddressDisplayName(message->getFromAddress())); - cpimMessage.addMessageHeader(cpimFromHeader); - Cpim::ToHeader cpimToHeader(cpimAddressUri(message->getToAddress()), cpimAddressDisplayName(message->getToAddress())); - cpimMessage.addMessageHeader(cpimToHeader); + cpimMessage.addMessageHeader( + Cpim::FromHeader(cpimAddressUri(message->getFromAddress()), cpimAddressDisplayName(message->getFromAddress())) + ); + cpimMessage.addMessageHeader( + Cpim::ToHeader(cpimAddressUri(message->getToAddress()), cpimAddressDisplayName(message->getToAddress())) + ); + cpimMessage.addMessageHeader( + Cpim::DateTimeHeader(message->getTime()) + ); if (message->getPrivate()->getPositiveDeliveryNotificationRequired() || message->getPrivate()->getNegativeDeliveryNotificationRequired() || message->getPrivate()->getDisplayNotificationRequired() ) { const string imdnNamespace = "imdn"; - Cpim::NsHeader cpimNsHeader(imdnNamespace, ""); - cpimMessage.addMessageHeader(cpimNsHeader); + cpimMessage.addMessageHeader(Cpim::NsHeader("urn:ietf:params:imdn", imdnNamespace)); char token[13]; belle_sip_random_token(token, sizeof(token)); - Cpim::GenericHeader cpimMessageIdHeader; - cpimMessageIdHeader.setName("Message-ID"); // TODO: Replace by imdnNamespace + ".Message-ID"); - cpimMessageIdHeader.setValue(token); - cpimMessage.addMessageHeader(cpimMessageIdHeader); + cpimMessage.addMessageHeader( + Cpim::GenericHeader("Message-ID", token) // TODO: Replace by imdnNamespace + ".Message-ID"); + ); message->getPrivate()->setImdnMessageId(token); - Cpim::GenericHeader dispositionNotificationHeader; - dispositionNotificationHeader.setName(imdnNamespace + ".Disposition-Notification"); vector dispositionNotificationValues; if (message->getPrivate()->getPositiveDeliveryNotificationRequired()) dispositionNotificationValues.emplace_back("positive-delivery"); @@ -68,8 +69,12 @@ ChatMessageModifier::Result CpimChatMessageModifier::encode (const shared_ptrgetPrivate()->getDisplayNotificationRequired()) dispositionNotificationValues.emplace_back("display"); - dispositionNotificationHeader.setValue(Utils::join(dispositionNotificationValues, ", ")); - cpimMessage.addMessageHeader(dispositionNotificationHeader); + cpimMessage.addMessageHeader( + Cpim::GenericHeader( + imdnNamespace + ".Disposition-Notification", + Utils::join(dispositionNotificationValues, ", ") + ) + ); } const Content *content; @@ -85,13 +90,16 @@ ChatMessageModifier::Result CpimChatMessageModifier::encode (const shared_ptrgetBodyAsString(); if (content->getContentDisposition().isValid()) { - Cpim::GenericHeader contentDispositionHeader("Content-Disposition", content->getContentDisposition().asString()); - cpimMessage.addContentHeader(contentDispositionHeader); + cpimMessage.addContentHeader( + Cpim::GenericHeader("Content-Disposition", content->getContentDisposition().asString()) + ); } - Cpim::GenericHeader contentTypeHeader("Content-Type", content->getContentType().asString()); - cpimMessage.addContentHeader(contentTypeHeader); - Cpim::GenericHeader contentLengthHeader("Content-Length", to_string(contentBody.size())); - cpimMessage.addContentHeader(contentLengthHeader); + cpimMessage.addContentHeader( + Cpim::GenericHeader("Content-Type", content->getContentType().asString()) + ); + cpimMessage.addContentHeader( + Cpim::GenericHeader("Content-Length", to_string(contentBody.size())) + ); cpimMessage.setContent(contentBody); Content newContent; @@ -116,76 +124,70 @@ ChatMessageModifier::Result CpimChatMessageModifier::decode (const shared_ptrgetBodyAsString(); const shared_ptr cpimMessage = Cpim::Message::createFromString(contentBody); - if (!cpimMessage) { + if (!cpimMessage || !cpimMessage->getMessageHeader("From") || !cpimMessage->getMessageHeader("To")) { lError() << "[CPIM] Message is invalid: " << contentBody; errorCode = 500; return ChatMessageModifier::Result::Error; } Content newContent; - bool contentTypeFound = false; - Cpim::Message::HeaderList l = cpimMessage->getContentHeaders(); - if (l) { - for (const auto &header : *l.get()) { - if (header->getName() == "Content-Disposition") { - newContent.setContentDisposition(ContentDisposition(header->getValue())); - } else if (header->getName() == "Content-Type") { - contentTypeFound = true; - newContent.setContentType(ContentType(header->getValue())); - } - } - } - if (!contentTypeFound) { + auto contentTypeHeader = cpimMessage->getContentHeader("Content-Type"); + if (!contentTypeHeader) { lError() << "[CPIM] No Content-type for the content of the message"; errorCode = 500; return ChatMessageModifier::Result::Error; } + newContent.setContentType(ContentType(contentTypeHeader->getValue())); + auto contentDispositionHeader = cpimMessage->getContentHeader("Content-Disposition"); + if (contentDispositionHeader) + newContent.setContentDisposition(ContentDisposition(contentDispositionHeader->getValue())); newContent.setBody(cpimMessage->getContent()); message->getPrivate()->setPositiveDeliveryNotificationRequired(false); message->getPrivate()->setNegativeDeliveryNotificationRequired(false); message->getPrivate()->setDisplayNotificationRequired(false); - Address cpimFromAddress; - Address cpimToAddress; - l = cpimMessage->getMessageHeaders(); - if (l) { - string imdnNamespace = ""; - for (const auto &header : *l.get()) { - if (header->getName() == "NS") { - string val = header->getValue(); - size_t startPos = 0; - startPos = val.find("<", startPos); - if (startPos == string::npos) - break; - size_t endPos = 0; - endPos = val.find(">", startPos); - if (endPos == string::npos) - break; - if (val.substr(startPos, endPos) == "") - imdnNamespace = Utils::trim(val.substr(0, startPos)); - } - } - for (const auto &header : *l.get()) { - if (header->getName() == "From") - cpimFromAddress = Address(header->getValue()); - else if (header->getName() == "To") - cpimToAddress = Address(header->getValue()); - else if ((header->getName() == "Message-ID") || (header->getName() == (imdnNamespace + ".Message-ID"))) - message->getPrivate()->setImdnMessageId(header->getValue()); - else if ((header->getName() == (imdnNamespace + ".Disposition-Notification"))) { - vector values = Utils::split(header->getValue(), ", "); - for (const auto &value : values) - if (value == "positive-delivery") - message->getPrivate()->setPositiveDeliveryNotificationRequired(true); - else if (value == "negative-delivery") - message->getPrivate()->setNegativeDeliveryNotificationRequired(true); - else if (value == "display") - message->getPrivate()->setDisplayNotificationRequired(true); + string imdnNamespace = ""; + auto messageHeaders = cpimMessage->getMessageHeaders(); + if (messageHeaders) { + for (const auto &header : *messageHeaders.get()) { + if (header->getName() != "NS") + continue; + auto nsHeader = static_pointer_cast(header); + if (nsHeader->getUri() == "urn:ietf:params:imdn") { + imdnNamespace = nsHeader->getPrefixName(); + break; } } } + auto fromHeader = static_pointer_cast(cpimMessage->getMessageHeader("From")); + Address cpimFromAddress(fromHeader->getValue()); + auto toHeader = static_pointer_cast(cpimMessage->getMessageHeader("To")); + Address cpimToAddress(toHeader->getValue()); + auto dateTimeHeader = static_pointer_cast(cpimMessage->getMessageHeader("DateTime")); + if (dateTimeHeader) + message->getPrivate()->setTime(dateTimeHeader->getTime()); + + auto messageIdHeader = cpimMessage->getMessageHeader("Message-ID"); // TODO: For compatibility, to remove + if (!imdnNamespace.empty()) { + if (!messageIdHeader) + messageIdHeader = cpimMessage->getMessageHeader("Message-ID", imdnNamespace); + auto dispositionNotificationHeader = cpimMessage->getMessageHeader("Disposition-Notification", imdnNamespace); + if (dispositionNotificationHeader) { + vector values = Utils::split(dispositionNotificationHeader->getValue(), ", "); + for (const auto &value : values) + if (value == "positive-delivery") + message->getPrivate()->setPositiveDeliveryNotificationRequired(true); + else if (value == "negative-delivery") + message->getPrivate()->setNegativeDeliveryNotificationRequired(true); + else if (value == "display") + message->getPrivate()->setDisplayNotificationRequired(true); + } + } + if (messageIdHeader) + message->getPrivate()->setImdnMessageId(messageIdHeader->getValue()); + // Modify the initial message since there was no error message->setInternalContent(newContent); if (cpimFromAddress.isValid())