Merge remote-tracking branch 'origin/dev_content_cpp' into dev_chatroom_list_subscription

This commit is contained in:
Benjamin Reis 2018-03-28 09:27:15 +02:00
commit d7fcc06dd0
21 changed files with 264 additions and 79 deletions

View file

@ -446,3 +446,7 @@ const char * sal_body_handler_get_header(const SalBodyHandler *body_handler, con
}
return NULL;
}
const belle_sip_list_t* sal_body_handler_get_headers(const SalBodyHandler *body_handler) {
return belle_sip_body_handler_get_headers(BELLE_SIP_BODY_HANDLER(body_handler));
}

View file

@ -25,6 +25,7 @@
#include "content/content.h"
#include "content/content-type.h"
#include "content/header/header-param.h"
#include "content/header/header.h"
#include "content/content-manager.h"
#include "content/file-content.h"
#include "content/file-transfer-content.h"
@ -259,6 +260,13 @@ static LinphoneContent * linphone_content_new_with_body_handler(SalBodyHandler *
belle_sip_free(body);
}
belle_sip_list_t *headers = (belle_sip_list_t *)sal_body_handler_get_headers(body_handler);
while (headers) {
belle_sip_header_t *cHeader = BELLE_SIP_HEADER(headers->data);
LinphonePrivate::Header header = LinphonePrivate::Header(belle_sip_header_get_name(cHeader), belle_sip_header_get_unparsed_value(cHeader));
L_GET_CPP_PTR_FROM_C_OBJECT(content)->addHeader(header);
headers = headers->next;
}
if (sal_body_handler_get_encoding(body_handler)) linphone_content_set_encoding(content, sal_body_handler_get_encoding(body_handler));
}
@ -307,12 +315,7 @@ SalBodyHandler * sal_body_handler_from_content(const LinphoneContent *content) {
}
for (const auto &header : L_GET_CPP_PTR_FROM_C_OBJECT(content)->getHeaders()) {
belle_sip_header_t *additionalHeader = BELLE_SIP_HEADER(
belle_sip_header_create(
header.first.c_str(),
header.second.c_str()
)
);
belle_sip_header_t *additionalHeader = belle_sip_header_parse(header.asString().c_str());
belle_sip_body_handler_add_header(BELLE_SIP_BODY_HANDLER(body_handler), additionalHeader);
}

View file

@ -650,6 +650,7 @@ SalBodyHandler * sal_body_handler_get_part(const SalBodyHandler *body_handler, i
const belle_sip_list_t * sal_body_handler_get_parts(const SalBodyHandler *body_handler);
SalBodyHandler * sal_body_handler_find_part_by_header(const SalBodyHandler *body_handler, const char *header_name, const char *header_value);
const char * sal_body_handler_get_header(const SalBodyHandler *body_handler, const char *header_name);
const belle_sip_list_t* sal_body_handler_get_headers(const SalBodyHandler *body_handler);
/*this function parses a document with key=value pairs separated by new lines, and extracts the value for a given key*/
int sal_lines_get_value(const char *data, const char *key, char *value, size_t value_size);

View file

@ -582,7 +582,7 @@ LinphoneReason ChatMessagePrivate::receive () {
foundSupportContentType = true;
break;
} else
lError() << "Unsupported content-type: " << c->getContentType().asString();
lError() << "Unsupported content-type: " << c->getContentType();
}
if (!foundSupportContentType) {

View file

@ -98,7 +98,7 @@ ChatMessageModifier::Result CpimChatMessageModifier::decode (const shared_ptr<Ch
content = message->getContents().front();
if (content->getContentType() != ContentType::Cpim) {
lError() << "[CPIM] Message is not CPIM but " << content->getContentType().asString();
lError() << "[CPIM] Message is not CPIM but " << content->getContentType();
return ChatMessageModifier::Result::Skipped;
}

View file

@ -22,6 +22,7 @@
#include "chat/chat-message/chat-message.h"
#include "content/content-type.h"
#include "content/header/header.h"
#include "content/content-manager.h"
#include "content/file-transfer-content.h"
@ -55,8 +56,8 @@ ChatMessageModifier::Result MultipartChatMessageModifier::decode (const shared_p
content->setContentType(c.getContentType());
content->setContentDisposition(c.getContentDisposition());
content->setContentEncoding(c.getContentEncoding());
for (const pair<string, string> &pair : c.getHeaders()) {
content->addHeader(pair.first, pair.second);
for (const Header &header : c.getHeaders()) {
content->addHeader(header);
}
content->setBodyFromUtf8(c.getBodyAsUtf8String());
} else {

View file

@ -156,7 +156,7 @@ void RemoteConferenceListEventHandler::notifyReceived (const Content *notifyCont
continue;
}
const string &cid = content.getHeaderValue("Content-Id");
const string &cid = content.getHeader("Content-Id").getValue();
if (cid.empty())
continue;

View file

@ -29,13 +29,15 @@
LINPHONE_BEGIN_NAMESPACE
class Header;
class ContentPrivate : public ClonableObjectPrivate {
private:
std::vector<char> body;
ContentType contentType;
ContentDisposition contentDisposition;
std::string contentEncoding;
std::list<std::pair<std::string, std::string>> headers;
std::list<Header> headers;
const std::list<std::pair<std::string, std::string>>::const_iterator findHeader (const std::string &headerName) const;

View file

@ -147,6 +147,7 @@ bool ContentType::setType (const string &type) {
L_D();
if (type.find('/') == string::npos) {
d->type = Utils::stringToLower(type);
setValue(d->type + "/" + d->subType);
return true;
}
return false;
@ -161,6 +162,7 @@ bool ContentType::setSubType (const string &subType) {
L_D();
if (subType.find('/') == string::npos) {
d->subType = Utils::stringToLower(subType);
setValue(d->type + "/" + d->subType);
return true;
}
return false;
@ -176,19 +178,6 @@ bool ContentType::isValid () const {
return !d->type.empty() && !d->subType.empty();
}
string ContentType::asString () const {
L_D();
if (isValid()) {
string asString = d->type + "/" + d->subType;
for (auto it = std::begin(getParameters()); it!=std::end(getParameters()); ++it) {
HeaderParam param = *it;
asString += param.asString();
}
return asString;
}
return "";
}
bool ContentType::isMultipart() const {
return getType() == "multipart";
}

View file

@ -58,8 +58,6 @@ public:
const std::string &getSubType () const;
bool setSubType (const std::string &subType);
std::string asString () const;
bool isMultipart() const;
static bool isFile (const ContentType &contentType);

View file

@ -25,6 +25,7 @@
#include "content-p.h"
#include "content-type.h"
#include "header/header.h"
// =============================================================================
@ -32,14 +33,6 @@ using namespace std;
LINPHONE_BEGIN_NAMESPACE
// -----------------------------------------------------------------------------
const list<pair<string, string>>::const_iterator ContentPrivate::findHeader (const string &headerName) const {
return findIf(headers, [&headerName](const pair<string, string> &pair) {
return pair.first == headerName;
});
}
// =============================================================================
Content::Content () : ClonableObject(*new ContentPrivate) {}
@ -205,28 +198,42 @@ bool Content::isFileTransfer () const {
void Content::addHeader (const string &headerName, const string &headerValue) {
L_D();
removeHeader(headerName);
d->headers.push_back(make_pair(headerName, headerValue));
Header header = Header(headerName, headerValue);
d->headers.push_back(header);
}
const list<pair<string, string>> &Content::getHeaders () const {
void Content::addHeader (const Header &header) {
L_D();
removeHeader(header.getName());
d->headers.push_back(header);
}
const list<Header> &Content::getHeaders () const {
L_D();
return d->headers;
}
const Header &Content::getHeader (const string &headerName) const {
L_D();
list<Header>::const_iterator it = findHeader(headerName);
if (it != d->headers.cend()) {
return *it;
}
return Utils::getEmptyConstRefObject<Header>();
}
void Content::removeHeader (const string &headerName) {
L_D();
auto it = d->findHeader(headerName);
auto it = findHeader(headerName);
if (it != d->headers.cend())
d->headers.remove(*it);
}
const string &Content::getHeaderValue (const string &headerName) const {
list<Header>::const_iterator Content::findHeader (const string &headerName) const {
L_D();
auto it = d->findHeader(headerName);
if (it != d->headers.cend())
return (*it).second;
return Utils::getEmptyConstRefObject<string>();
return findIf(d->headers, [&headerName](const Header &header) {
return header.getName() == headerName;
});
}
LINPHONE_END_NAMESPACE

View file

@ -35,6 +35,7 @@ LINPHONE_BEGIN_NAMESPACE
class ContentDisposition;
class ContentType;
class ContentPrivate;
class Header;
class LINPHONE_PUBLIC Content : public ClonableObject, public AppDataContainer {
public:
@ -76,10 +77,12 @@ public:
virtual bool isFile () const;
virtual bool isFileTransfer () const;
const std::list<std::pair<std::string, std::string>> &getHeaders () const;
const std::list<Header> &getHeaders () const;
const Header &getHeader (const std::string &headerName) const;
void addHeader (const std::string &headerName, const std::string &headerValue);
void addHeader (const Header &header);
void removeHeader (const std::string &headerName);
const std::string &getHeaderValue (const std::string &headerName) const;
std::list<Header>::const_iterator findHeader (const std::string &headerName) const;
protected:
explicit Content (ContentPrivate &p);

View file

@ -32,6 +32,8 @@ LINPHONE_BEGIN_NAMESPACE
class HeaderPrivate : public ClonableObjectPrivate {
private:
std::string name;
std::string value;
std::list<HeaderParam> parameters;
L_DECLARE_PUBLIC(Header);
};

View file

@ -17,6 +17,8 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include <sstream>
#include "linphone/utils/utils.h"
#include "linphone/utils/algorithm.h"
@ -31,22 +33,93 @@ LINPHONE_BEGIN_NAMESPACE
// -----------------------------------------------------------------------------
Header::Header(HeaderPrivate &p) : ClonableObject(p) {
Header::Header(HeaderPrivate &p) : ClonableObject(p) {}
Header::Header() : ClonableObject(*new HeaderPrivate) {}
Header::Header (const string &name, const string &value) : ClonableObject(*new HeaderPrivate) {
setName(name);
size_t posParam = value.find(";");
if (posParam == string::npos) {
setValue(value);
return;
}
string parsedValue = value.substr(0, posParam);
string params = value.substr(posParam + 1);
string token;
do {
posParam = params.find(";");
if (posParam == string::npos) {
token = params;
} else {
token = params.substr(0, posParam);
}
addParameter(HeaderParam(token));
params.erase(0, posParam + 1);
} while (posParam != std::string::npos);
setValue(parsedValue);
}
void Header::cleanParameters() {
Header::Header (const string &name, const string &value, const list<HeaderParam> &params) : Header(name, value) {
addParameters(params);
}
Header::Header (const Header &other) : Header(other.getName(), other.getValue(), other.getParameters()) {}
Header &Header::operator= (const Header &other) {
if (this != &other) {
setName(other.getName());
setValue(other.getValue());
cleanParameters();
addParameters(other.getParameters());
}
return *this;
}
bool Header::operator== (const Header &other) const {
return getName() == other.getName() &&
getValue() == other.getValue();
}
bool Header::operator!= (const Header &other) const {
return !(*this == other);
}
void Header::setName (const string &name) {
L_D();
d->name = name;
}
string Header::getName () const {
L_D();
return d->name;
}
void Header::setValue (const string &value) {
L_D();
d->value = value;
}
string Header::getValue () const {
L_D();
return d->value;
}
void Header::cleanParameters () {
L_D();
d->parameters.clear();
}
const std::list<HeaderParam> &Header::getParameters () const {
const list<HeaderParam> &Header::getParameters () const {
L_D();
return d->parameters;
}
void Header::addParameter (const std::string &paramName, const std::string &paramValue) {
void Header::addParameter (const string &paramName, const string &paramValue) {
addParameter(HeaderParam(paramName, paramValue));
}
@ -56,14 +129,14 @@ void Header::addParameter (const HeaderParam &param) {
d->parameters.push_back(param);
}
void Header::addParameters(const std::list<HeaderParam> &params) {
void Header::addParameters(const list<HeaderParam> &params) {
for (auto it = std::begin(params); it!=std::end(params); ++it) {
HeaderParam param = *it;
addParameter(param.getName(), param.getValue());
}
}
void Header::removeParameter (const std::string &paramName) {
void Header::removeParameter (const string &paramName) {
L_D();
auto it = findParameter(paramName);
if (it != d->parameters.cend())
@ -74,20 +147,37 @@ void Header::removeParameter (const HeaderParam &param) {
removeParameter(param.getName());
}
std::list<HeaderParam>::const_iterator Header::findParameter (const std::string &paramName) const {
list<HeaderParam>::const_iterator Header::findParameter (const string &paramName) const {
L_D();
return findIf(d->parameters, [&paramName](const HeaderParam &param) {
return param.getName() == paramName;
});
}
const HeaderParam &Header::getParameter (const std::string &paramName) const {
const HeaderParam &Header::getParameter (const string &paramName) const {
L_D();
std::list<HeaderParam>::const_iterator it = findParameter(paramName);
list<HeaderParam>::const_iterator it = findParameter(paramName);
if (it != d->parameters.cend()) {
return *it;
}
return Utils::getEmptyConstRefObject<HeaderParam>();
}
string Header::asString () const {
stringstream asString;
if (!getName().empty()) {
asString << getName() << ":";
}
asString << getValue();
for (const auto &param : getParameters()) {
asString << param.asString();
}
return asString.str();
}
ostream &operator<<(ostream& stream, const Header& header) {
stream << header.asString();
return stream;
}
LINPHONE_END_NAMESPACE

View file

@ -33,7 +33,23 @@ class HeaderParam;
class LINPHONE_PUBLIC Header : public ClonableObject {
public:
void cleanParameters();
Header ();
Header (const std::string &name, const std::string &value);
Header (const std::string &name, const std::string &value, const std::list<HeaderParam> &params);
Header (const Header &other);
Header &operator= (const Header &other);
bool operator== (const Header &other) const;
bool operator!= (const Header &other) const;
void setName (const std::string &name);
std::string getName () const;
void setValue (const std::string &value);
std::string getValue () const;
void cleanParameters ();
const std::list<HeaderParam> &getParameters () const;
void addParameter (const std::string &paramName, const std::string &paramValue);
void addParameter (const HeaderParam &param);
@ -43,6 +59,9 @@ public:
std::list<HeaderParam>::const_iterator findParameter (const std::string &paramName) const;
const HeaderParam &getParameter (const std::string &paramName) const;
std::string asString () const;
friend std::ostream &operator<<(std::ostream&, const Header&);
protected:
explicit Header (HeaderPrivate &p);

View file

@ -199,7 +199,7 @@ set(SOURCE_FILES_C
set(SOURCE_FILES_CXX
clonable-object-tester.cpp
conference-event-tester.cpp
content-manager-tester.cpp
contents-tester.cpp
cpim-tester.cpp
main-db-tester.cpp
multipart-tester.cpp

View file

@ -21,8 +21,10 @@
#include "content/content-manager.h"
#include "content/content-type.h"
#include "content/content.h"
#include "content/header/header-param.h"
#include "liblinphone_tester.h"
#include "tester_utils.h"
#include "logger/logger.h"
using namespace LinphonePrivate;
using namespace std;
@ -60,6 +62,7 @@ static const char* source_multipart = \
" </p1:person>" \
"</presence>" \
"-----------------------------14737809831466499882746641449\r\n" \
"Content-Encoding: b64\r\n" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n\r\n" \
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\" ?>" \
"<presence xmlns=\"urn:ietf:params:xml:ns:pidf\" entity=\"sip:+XXXXXXXXXX@sip.linphone.org;user=phone\" xmlns:p1=\"urn:ietf:params:xml:ns:pidf:data-model\">" \
@ -77,6 +80,7 @@ static const char* source_multipart = \
" </p1:person>" \
"</presence>" \
"-----------------------------14737809831466499882746641449\r\n" \
"Content-Id: toto;param1=value1;param2;param3=value3\r\n" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n\r\n" \
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\" ?>" \
"<presence xmlns=\"urn:ietf:params:xml:ns:pidf\" entity=\"sip:+ZZZZZZZZZZ@sip.linphone.org;user=phone\" xmlns:p1=\"urn:ietf:params:xml:ns:pidf:data-model\">" \
@ -97,8 +101,8 @@ static const char* source_multipart = \
static const char* generated_multipart = \
"-----------------------------14737809831466499882746641449\r\n" \
"Content-Type: application/rlmi+xml;charset=\"UTF-8\"\r\n\r\n" \
"Content-Length:582" \
"Content-Type: application/rlmi+xml;charset=\"UTF-8\"\r\n" \
"Content-Length:582\r\n\r\n" \
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\" ?>" \
"<list xmlns=\"urn:ietf:params:xml:ns:rlmi\" fullState=\"false\" uri=\"sip:rls@sip.linphone.org\" version=\"1\">" \
" <resource uri=\"sip:+YYYYYYYYYY@sip.linphone.org;user=phone\">" \
@ -112,8 +116,8 @@ static const char* generated_multipart = \
" </resource>" \
"</list>" \
"-----------------------------14737809831466499882746641449\r\n" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n\r\n" \
"Content-Length:561" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n" \
"Content-Length:561\r\n\r\n" \
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\" ?>" \
"<presence xmlns=\"urn:ietf:params:xml:ns:pidf\" entity=\"sip:+YYYYYYYYYY@sip.linphone.org;user=phone\" xmlns:p1=\"urn:ietf:params:xml:ns:pidf:data-model\">" \
" <tuple id=\"qmht-9\">" \
@ -130,8 +134,9 @@ static const char* generated_multipart = \
" </p1:person>" \
"</presence>" \
"-----------------------------14737809831466499882746641449\r\n" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n\r\n" \
"Content-Length:561" \
"Content-Encoding:b64\r\n" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n" \
"Content-Length:561\r\n\r\n" \
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\" ?>" \
"<presence xmlns=\"urn:ietf:params:xml:ns:pidf\" entity=\"sip:+XXXXXXXXXX@sip.linphone.org;user=phone\" xmlns:p1=\"urn:ietf:params:xml:ns:pidf:data-model\">" \
" <tuple id=\"szohvt\">" \
@ -148,8 +153,9 @@ static const char* generated_multipart = \
" </p1:person>" \
"</presence>" \
"-----------------------------14737809831466499882746641449\r\n" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n\r\n" \
"Content-Length:546" \
"Content-Id:toto;param1=value1;param2;param3=value3\r\n" \
"Content-Type: application/pidf+xml;charset=\"UTF-8\"\r\n" \
"Content-Length:546\r\n\r\n" \
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\" ?>" \
"<presence xmlns=\"urn:ietf:params:xml:ns:pidf\" entity=\"sip:+ZZZZZZZZZZ@sip.linphone.org;user=phone\" xmlns:p1=\"urn:ietf:params:xml:ns:pidf:data-model\">" \
" <tuple id=\"oc3e08\">" \
@ -292,6 +298,7 @@ void multipart_to_list () {
ms_message("\n\n----- Original part 3 -----");
ms_message("%s", originalStr3.c_str());
BC_ASSERT_TRUE(originalStr3 == generatedStr3);
BC_ASSERT_TRUE(content3.getHeader("Content-Encoding").getValue() == "b64");
Content content4 = contents.front();
contents.pop_front();
@ -310,6 +317,10 @@ void multipart_to_list () {
ms_message("\n\n----- Original part 4 -----");
ms_message("%s", originalStr4.c_str());
BC_ASSERT_TRUE(originalStr4 == generatedStr4);
BC_ASSERT_TRUE(content4.getHeader("Content-Id").getValue() == "toto");
BC_ASSERT_TRUE(content4.getHeader("Content-Id").getParameter("param1").getValue() == "value1");
BC_ASSERT_TRUE(content4.getHeader("Content-Id").getParameter("param2").getValue().empty());
BC_ASSERT_TRUE(content4.getHeader("Content-Id").getParameter("param3").getValue() == "value3");
}
void list_to_multipart () {
@ -325,8 +336,14 @@ void list_to_multipart () {
content2.setContentType(contentType);
Content content3;
content3.setBody(part3);
content3.addHeader("Content-Encoding", "b64");
content3.setContentType(contentType);
Content content4;
Header header = Header("Content-Id", "toto");
header.addParameter("param1", "value1");
header.addParameter("param2", "");
header.addParameter("param3", "value3");
content4.addHeader(header);
content4.setBody(part4);
content4.setContentType(contentType);
list<Content *> contents = {&content1, &content2, &content3, &content4};
@ -353,24 +370,66 @@ void list_to_multipart () {
}
static void content_type_parsing(void) {
const string type = "message/external-body;access-type=URL;URL=\"https://www.linphone.org/img/linphone-open-source-voip-projectX2.png\"";
string type = "message/external-body;access-type=URL;URL=\"https://www.linphone.org/img/linphone-open-source-voip-projectX2.png\"";
ContentType contentType = ContentType(type);
BC_ASSERT_STRING_EQUAL("message", contentType.getType().c_str());
BC_ASSERT_STRING_EQUAL("external-body", contentType.getSubType().c_str());
BC_ASSERT_STRING_EQUAL("URL", contentType.getParameter("access-type").getValue().c_str());
BC_ASSERT_STRING_EQUAL("\"https://www.linphone.org/img/linphone-open-source-voip-projectX2.png\"", contentType.getParameter("URL").getValue().c_str());
BC_ASSERT_STRING_EQUAL("", contentType.getParameter("boundary").getValue().c_str());
BC_ASSERT_EQUAL(2, contentType.getParameters().size(), int, "%d");
lInfo() << "Content-Type is " << contentType;
BC_ASSERT_TRUE(type == contentType.asString());
type = "multipart/mixed;boundary=-----------------------------14737809831466499882746641450";
contentType = ContentType(type);
BC_ASSERT_STRING_EQUAL("multipart", contentType.getType().c_str());
BC_ASSERT_STRING_EQUAL("mixed", contentType.getSubType().c_str());
BC_ASSERT_STRING_EQUAL("-----------------------------14737809831466499882746641450", contentType.getParameter("boundary").getValue().c_str());
BC_ASSERT_STRING_EQUAL("", contentType.getParameter("access-type").getValue().c_str());
BC_ASSERT_EQUAL(1, contentType.getParameters().size(), int, "%d");
lInfo() << "Content-Type is " << contentType;
BC_ASSERT_TRUE(type == contentType.asString());
type = "plain/text";
contentType = ContentType(type);
BC_ASSERT_STRING_EQUAL("plain", contentType.getType().c_str());
BC_ASSERT_STRING_EQUAL("text", contentType.getSubType().c_str());
BC_ASSERT_STRING_EQUAL("", contentType.getParameter("boundary").getValue().c_str());
BC_ASSERT_EQUAL(0, contentType.getParameters().size(), int, "%d");
lInfo() << "Content-Type is " << contentType;
BC_ASSERT_TRUE(type == contentType.asString());
}
test_t content_manager_tests[] = {
static void content_header_parsing(void) {
string value = "toto;param1=value1;param2;param3=value3";
Header header = Header("Content-Id", value);
BC_ASSERT_TRUE(header.getValue() == "toto");
BC_ASSERT_TRUE(header.getParameter("param1").getValue() == "value1");
BC_ASSERT_TRUE(header.getParameter("param2").getValue().empty());
BC_ASSERT_TRUE(header.getParameter("param3").getValue() == "value3");
BC_ASSERT_EQUAL(3, header.getParameters().size(), int, "%d");
BC_ASSERT_STRING_EQUAL("", header.getParameter("encoding").getValue().c_str());
value = "b64";
header = Header("Content-Encoding", value);
BC_ASSERT_TRUE(header.getValue() == value);
BC_ASSERT_EQUAL(0, header.getParameters().size(), int, "%d");
BC_ASSERT_STRING_EQUAL("", header.getParameter("access-type").getValue().c_str());
}
test_t contents_tests[] = {
TEST_NO_TAG("Multipart to list", multipart_to_list),
TEST_NO_TAG("List to multipart", list_to_multipart),
TEST_NO_TAG("Content type parsing", content_type_parsing)
TEST_NO_TAG("Content type parsing", content_type_parsing),
TEST_NO_TAG("Content header parsing", content_header_parsing)
};
test_suite_t content_manager_test_suite = {
"Content manager",
test_suite_t contents_test_suite = {
"Contents",
nullptr,
nullptr,
liblinphone_tester_before_each,
liblinphone_tester_after_each,
sizeof(content_manager_tests) / sizeof(content_manager_tests[0]), content_manager_tests
sizeof(contents_tests) / sizeof(contents_tests[0]), contents_tests
};

View file

@ -45,7 +45,7 @@ extern test_suite_t call_video_test_suite;
extern test_suite_t clonable_object_test_suite;
extern test_suite_t conference_event_test_suite;
extern test_suite_t conference_test_suite;
extern test_suite_t content_manager_test_suite;
extern test_suite_t contents_test_suite;
extern test_suite_t cpim_test_suite;
extern test_suite_t dtmf_test_suite;
extern test_suite_t event_test_suite;

View file

@ -2294,15 +2294,19 @@ void text_message_with_custom_content_type_and_lime(void) {
static int im_encryption_engine_process_incoming_message_cb(LinphoneImEncryptionEngine *engine, LinphoneChatRoom *room, LinphoneChatMessage *msg) {
ms_debug("IM encryption process incoming message with content type %s", linphone_chat_message_get_content_type(msg));
if (linphone_chat_message_get_content_type(msg)) {
if (strcmp(linphone_chat_message_get_content_type(msg), "cipher/b64") == 0) {
size_t b64Size = 0;
unsigned char *output;
bctbx_base64_decode(NULL, &b64Size, (unsigned char *)linphone_chat_message_get_text(msg), strlen(linphone_chat_message_get_text(msg)));
const char *data = linphone_chat_message_get_text(msg);
ms_debug("IM encryption process incoming message crypted message is %s", data);
bctbx_base64_decode(NULL, &b64Size, (unsigned char *)data, strlen(data));
output = (unsigned char *)ms_malloc(b64Size+1),
bctbx_base64_decode(output, &b64Size, (unsigned char *)linphone_chat_message_get_text(msg), strlen(linphone_chat_message_get_text(msg)));
bctbx_base64_decode(output, &b64Size, (unsigned char *)data, strlen(data));
output[b64Size] = '\0';
linphone_chat_message_set_text(msg, (char *)output);
ms_debug("IM encryption process incoming message decrypted message is %s", output);
ms_free(output);
linphone_chat_message_set_content_type(msg, "text/plain");
return 0;

View file

@ -430,8 +430,10 @@ static void test_presence_list_base(bool_t enable_compression) {
lcs = bctbx_list_append(lcs, pauline->lc);
wait_for_list(lcs, &laure->stat.number_of_NotifyPresenceReceived, 2, 4000);
BC_ASSERT_EQUAL(laure->stat.number_of_NotifyPresenceReceived, 2, int, "%d");
BC_ASSERT_EQUAL(linphone_friend_list_get_expected_notification_version(linphone_core_get_default_friend_list(laure->lc)), 1, int, "%d");
BC_ASSERT_GREATER(laure->stat.number_of_NotifyPresenceReceived, 2, int, "%d");
BC_ASSERT_LOWER(laure->stat.number_of_NotifyPresenceReceived, 3, int, "%d");
BC_ASSERT_GREATER(linphone_friend_list_get_expected_notification_version(linphone_core_get_default_friend_list(laure->lc)), 1, int, "%d");
BC_ASSERT_LOWER(linphone_friend_list_get_expected_notification_version(linphone_core_get_default_friend_list(laure->lc)), 2, int, "%d");
lf = linphone_friend_list_find_friend_by_address(linphone_core_get_default_friend_list(laure->lc), get_identity_address(marie));
if (!BC_ASSERT_PTR_NOT_NULL(lf)) goto end;
BC_ASSERT_EQUAL(linphone_friend_get_status(lf), LinphoneStatusBusy, int, "%d");
@ -485,7 +487,8 @@ static void test_presence_list_base(bool_t enable_compression) {
/* The number of PresenceReceived events can be 3 or 4 here. TODO: ideally it should always be 3. */
BC_ASSERT_GREATER(laure->stat.number_of_NotifyPresenceReceived, 3, int, "%d");
BC_ASSERT_LOWER(laure->stat.number_of_NotifyPresenceReceived, 4, int, "%d");
BC_ASSERT_EQUAL(linphone_friend_list_get_expected_notification_version(linphone_core_get_default_friend_list(laure->lc)), 2, int, "%d");
BC_ASSERT_GREATER(linphone_friend_list_get_expected_notification_version(linphone_core_get_default_friend_list(laure->lc)), 2, int, "%d");
BC_ASSERT_LOWER(linphone_friend_list_get_expected_notification_version(linphone_core_get_default_friend_list(laure->lc)), 3, int, "%d");
lf = linphone_friend_list_find_friend_by_address(linphone_core_get_default_friend_list(laure->lc), get_identity_address(marie));
BC_ASSERT_EQUAL(linphone_friend_get_status(lf), LinphoneStatusOnThePhone, int, "%d");

View file

@ -604,7 +604,7 @@ void liblinphone_tester_add_suites() {
bc_tester_add_suite(&stun_test_suite);
bc_tester_add_suite(&event_test_suite);
bc_tester_add_suite(&conference_event_test_suite);
bc_tester_add_suite(&content_manager_test_suite);
bc_tester_add_suite(&contents_test_suite);
bc_tester_add_suite(&flexisip_test_suite);
bc_tester_add_suite(&remote_provisioning_test_suite);
bc_tester_add_suite(&quality_reporting_test_suite);