summaryrefslogtreecommitdiff
path: root/test/integration-http-server.cpp
diff options
context:
space:
mode:
authorMichael Meeks <michael.meeks@collabora.com>2016-11-24 14:52:34 +0000
committerMichael Meeks <michael.meeks@collabora.com>2016-11-25 09:58:48 +0000
commitcca657c8f2031ec88366c52f5e8e10c2e04129f9 (patch)
treea2273ed56080856d8494ba759b8ed0e435ebba99 /test/integration-http-server.cpp
parent4432aba25b6ee68356e0ddfc724afb8373651945 (diff)
Apply the pre-branch rename script to re-organize the source.
Diffstat (limited to 'test/integration-http-server.cpp')
-rw-r--r--test/integration-http-server.cpp288
1 files changed, 288 insertions, 0 deletions
diff --git a/test/integration-http-server.cpp b/test/integration-http-server.cpp
new file mode 100644
index 000000000..9ca4ec19d
--- /dev/null
+++ b/test/integration-http-server.cpp
@@ -0,0 +1,288 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include "config.h"
+
+#include <Poco/Net/AcceptCertificateHandler.h>
+#include <Poco/Net/FilePartSource.h>
+#include <Poco/Net/HTMLForm.h>
+#include <Poco/Net/HTTPClientSession.h>
+#include <Poco/Net/HTTPRequest.h>
+#include <Poco/Net/HTTPResponse.h>
+#include <Poco/Net/HTTPSClientSession.h>
+#include <Poco/Net/InvalidCertificateHandler.h>
+#include <Poco/Net/PrivateKeyPassphraseHandler.h>
+#include <Poco/Net/SSLManager.h>
+#include <Poco/RegularExpression.h>
+#include <Poco/StreamCopier.h>
+#include <Poco/URI.h>
+
+#include <cppunit/extensions/HelperMacros.h>
+
+#include <Common.hpp>
+#include "common/FileUtil.hpp"
+#include <Util.hpp>
+
+#include "countloolkits.hpp"
+#include "helpers.hpp"
+
+/// Tests the HTTP GET API of loolwsd.
+class HTTPServerTest : public CPPUNIT_NS::TestFixture
+{
+ const Poco::URI _uri;
+ static int InitialLoolKitCount;
+
+ CPPUNIT_TEST_SUITE(HTTPServerTest);
+
+ CPPUNIT_TEST(testDiscovery);
+ CPPUNIT_TEST(testLoleafletGet);
+ CPPUNIT_TEST(testLoleafletPost);
+ CPPUNIT_TEST(testScriptsAndLinksGet);
+ CPPUNIT_TEST(testScriptsAndLinksPost);
+ CPPUNIT_TEST(testConvertTo);
+
+ CPPUNIT_TEST_SUITE_END();
+
+ void testCountHowManyLoolkits();
+
+ void testDiscovery();
+ void testLoleafletGet();
+ void testLoleafletPost();
+ void testScriptsAndLinksGet();
+ void testScriptsAndLinksPost();
+ void testConvertTo();
+
+ void testNoExtraLoolKitsLeft();
+
+public:
+ HTTPServerTest()
+ : _uri(helpers::getTestServerURI())
+ {
+#if ENABLE_SSL
+ Poco::Net::initializeSSL();
+ // Just accept the certificate anyway for testing purposes
+ Poco::SharedPtr<Poco::Net::InvalidCertificateHandler> invalidCertHandler = new Poco::Net::AcceptCertificateHandler(false);
+ Poco::Net::Context::Params sslParams;
+ Poco::Net::Context::Ptr sslContext = new Poco::Net::Context(Poco::Net::Context::CLIENT_USE, sslParams);
+ Poco::Net::SSLManager::instance().initializeClient(0, invalidCertHandler, sslContext);
+#endif
+ }
+
+ ~HTTPServerTest()
+ {
+#if ENABLE_SSL
+ Poco::Net::uninitializeSSL();
+#endif
+ }
+
+ void setUp()
+ {
+ testCountHowManyLoolkits();
+ }
+
+ void tearDown()
+ {
+ testNoExtraLoolKitsLeft();
+ }
+};
+
+int HTTPServerTest::InitialLoolKitCount = 1;
+
+void HTTPServerTest::testCountHowManyLoolkits()
+{
+ InitialLoolKitCount = countLoolKitProcesses(InitialLoolKitCount);
+ CPPUNIT_ASSERT(InitialLoolKitCount > 0);
+}
+
+void HTTPServerTest::testDiscovery()
+{
+ std::unique_ptr<Poco::Net::HTTPClientSession> session(helpers::createSession(_uri));
+
+ Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_GET, "/hosting/discovery");
+ session->sendRequest(request);
+
+ Poco::Net::HTTPResponse response;
+ session->receiveResponse(response);
+ CPPUNIT_ASSERT_EQUAL(Poco::Net::HTTPResponse::HTTP_OK, response.getStatus());
+ CPPUNIT_ASSERT_EQUAL(std::string("text/xml"), response.getContentType());
+}
+
+void HTTPServerTest::testLoleafletGet()
+{
+ std::unique_ptr<Poco::Net::HTTPClientSession> session(helpers::createSession(_uri));
+
+ Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_GET, "/loleaflet/dist/loleaflet.html?access_token=111111111");
+ Poco::Net::HTMLForm param(request);
+ session->sendRequest(request);
+
+ Poco::Net::HTTPResponse response;
+ std::istream& rs = session->receiveResponse(response);
+ CPPUNIT_ASSERT_EQUAL(Poco::Net::HTTPResponse::HTTP_OK, response.getStatus());
+ CPPUNIT_ASSERT_EQUAL(std::string("text/html"), response.getContentType());
+
+ std::string html;
+ Poco::StreamCopier::copyToString(rs, html);
+
+ CPPUNIT_ASSERT(html.find(param["access_token"]) != std::string::npos);
+ CPPUNIT_ASSERT(html.find(_uri.getHost()) != std::string::npos);
+ CPPUNIT_ASSERT(html.find(std::string(LOOLWSD_VERSION_HASH)) != std::string::npos);
+}
+
+void HTTPServerTest::testLoleafletPost()
+{
+ std::unique_ptr<Poco::Net::HTTPClientSession> session(helpers::createSession(_uri));
+
+ Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_POST, "/loleaflet/dist/loleaflet.html");
+ Poco::Net::HTMLForm form;
+ form.set("access_token", "2222222222");
+ form.prepareSubmit(request);
+ std::ostream& ostr = session->sendRequest(request);
+ form.write(ostr);
+
+ Poco::Net::HTTPResponse response;
+ std::istream& rs = session->receiveResponse(response);
+ CPPUNIT_ASSERT_EQUAL(Poco::Net::HTTPResponse::HTTP_OK, response.getStatus());
+
+ std::string html;
+ Poco::StreamCopier::copyToString(rs, html);
+
+ CPPUNIT_ASSERT(html.find(form["access_token"]) != std::string::npos);
+ CPPUNIT_ASSERT(html.find(_uri.getHost()) != std::string::npos);
+}
+
+namespace
+{
+
+void assertHTTPFilesExist(const Poco::URI& uri, Poco::RegularExpression& expr, const std::string& html, const std::string& mimetype = std::string())
+{
+ Poco::RegularExpression::MatchVec matches;
+ bool found = false;
+
+ for (int offset = 0; expr.match(html, offset, matches) > 0; offset = static_cast<int>(matches[0].offset + matches[0].length))
+ {
+ found = true;
+ CPPUNIT_ASSERT_EQUAL(2, (int)matches.size());
+ Poco::URI uriScript(html.substr(matches[1].offset, matches[1].length));
+ if (uriScript.getHost().empty())
+ {
+ std::string scriptString(uriScript.toString());
+
+ // ignore the branding bits, it's not an error when they aren't present.
+ if (scriptString.find("/branding.") != std::string::npos)
+ continue;
+
+ std::unique_ptr<Poco::Net::HTTPClientSession> session(helpers::createSession(uri));
+
+ Poco::Net::HTTPRequest requestScript(Poco::Net::HTTPRequest::HTTP_GET, scriptString);
+ session->sendRequest(requestScript);
+
+ Poco::Net::HTTPResponse responseScript;
+ session->receiveResponse(responseScript);
+ CPPUNIT_ASSERT_EQUAL(Poco::Net::HTTPResponse::HTTP_OK, responseScript.getStatus());
+
+ if (!mimetype.empty())
+ CPPUNIT_ASSERT_EQUAL(mimetype, responseScript.getContentType());
+ }
+ }
+
+ CPPUNIT_ASSERT_MESSAGE("No match found", found);
+}
+
+}
+
+void HTTPServerTest::testScriptsAndLinksGet()
+{
+ std::unique_ptr<Poco::Net::HTTPClientSession> session(helpers::createSession(_uri));
+
+ Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_GET, "/loleaflet/dist/loleaflet.html");
+ session->sendRequest(request);
+
+ Poco::Net::HTTPResponse response;
+ std::istream& rs = session->receiveResponse(response);
+ CPPUNIT_ASSERT_EQUAL(Poco::Net::HTTPResponse::HTTP_OK, response.getStatus());
+
+ std::string html;
+ Poco::StreamCopier::copyToString(rs, html);
+
+ Poco::RegularExpression script("<script.*?src=\"(.*?)\"");
+ assertHTTPFilesExist(_uri, script, html, "application/javascript");
+
+ Poco::RegularExpression link("<link.*?href=\"(.*?)\"");
+ assertHTTPFilesExist(_uri, link, html);
+}
+
+void HTTPServerTest::testScriptsAndLinksPost()
+{
+ std::unique_ptr<Poco::Net::HTTPClientSession> session(helpers::createSession(_uri));
+
+ Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_POST, "/loleaflet/dist/loleaflet.html");
+ std::string body;
+ request.setContentLength((int) body.length());
+ session->sendRequest(request) << body;
+
+ Poco::Net::HTTPResponse response;
+ std::istream& rs = session->receiveResponse(response);
+ CPPUNIT_ASSERT_EQUAL(Poco::Net::HTTPResponse::HTTP_OK, response.getStatus());
+
+ std::string html;
+ Poco::StreamCopier::copyToString(rs, html);
+
+ Poco::RegularExpression script("<script.*?src=\"(.*?)\"");
+ assertHTTPFilesExist(_uri, script, html, "application/javascript");
+
+ Poco::RegularExpression link("<link.*?href=\"(.*?)\"");
+ assertHTTPFilesExist(_uri, link, html);
+}
+
+void HTTPServerTest::testConvertTo()
+{
+ const auto srcPath = FileUtil::getTempFilePath(TDOC, "hello.odt");
+ std::unique_ptr<Poco::Net::HTTPClientSession> session(helpers::createSession(_uri));
+ session->setTimeout(Poco::Timespan(2, 0)); // 2 seconds.
+
+ Poco::Net::HTTPRequest request(Poco::Net::HTTPRequest::HTTP_POST, "/lool/convert-to");
+ Poco::Net::HTMLForm form;
+ form.setEncoding(Poco::Net::HTMLForm::ENCODING_MULTIPART);
+ form.set("format", "txt");
+ form.addPart("data", new Poco::Net::FilePartSource(srcPath));
+ form.prepareSubmit(request);
+ // If this results in a Poco::Net::ConnectionRefusedException, loolwsd is not running.
+ form.write(session->sendRequest(request));
+
+ Poco::Net::HTTPResponse response;
+ std::stringstream actualStream;
+ // receiveResponse() resulted in a Poco::Net::NoMessageException.
+ std::istream& responseStream = session->receiveResponse(response);
+ Poco::StreamCopier::copyStream(responseStream, actualStream);
+
+ std::ifstream fileStream(TDOC "/hello.txt");
+ std::stringstream expectedStream;
+ expectedStream << fileStream.rdbuf();
+
+ // Remove the temp files.
+ FileUtil::removeFile(srcPath);
+
+ // In some cases the result is prefixed with (the UTF-8 encoding of) the Unicode BOM
+ // (U+FEFF). Skip that.
+ std::string actualString = actualStream.str();
+ if (actualString.size() > 3 && actualString[0] == '\xEF' && actualString[1] == '\xBB' && actualString[2] == '\xBF')
+ actualString = actualString.substr(3);
+ CPPUNIT_ASSERT_EQUAL(expectedStream.str(), actualString);
+}
+
+void HTTPServerTest::testNoExtraLoolKitsLeft()
+{
+ const auto countNow = countLoolKitProcesses(InitialLoolKitCount);
+
+ CPPUNIT_ASSERT_EQUAL(InitialLoolKitCount, countNow);
+}
+
+CPPUNIT_TEST_SUITE_REGISTRATION(HTTPServerTest);
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */