From 3b1ad4bb8d4be45bd43f9eb3af068119561b1bcb Mon Sep 17 00:00:00 2001 From: Rashesh Padia Date: Wed, 14 Aug 2024 14:46:21 +0530 Subject: [PATCH] wip commit Signed-off-by: Rashesh Padia Change-Id: I848f853be8c14d3367f8501c603114a3e23a617b --- common/Util.hpp | 1 + docker/from-source-gh-action/Dockerfile | 4 +- docker/from-source-gh-action/build.sh | 2 +- wsd/Admin.cpp | 45 ++++++++++++++++++++- wsd/Admin.hpp | 34 ++++++++++++++++ wsd/ClientRequestDispatcher.cpp | 54 ++++++++++++++++++++++--- wsd/ProxyRequestHandler.cpp | 9 +++-- wsd/ProxyRequestHandler.hpp | 2 + 8 files changed, 140 insertions(+), 11 deletions(-) diff --git a/common/Util.hpp b/common/Util.hpp index ffa97aa80d94b..347755c6a5e86 100644 --- a/common/Util.hpp +++ b/common/Util.hpp @@ -41,6 +41,7 @@ #include #include +#include "config.h" #define STRINGIFY(X) #X diff --git a/docker/from-source-gh-action/Dockerfile b/docker/from-source-gh-action/Dockerfile index 9eb102fc4d1bb..0b3b5aaf44139 100644 --- a/docker/from-source-gh-action/Dockerfile +++ b/docker/from-source-gh-action/Dockerfile @@ -2,7 +2,9 @@ FROM ubuntu:24.04 AS builder ENV CORE_ASSETS https://github.com/CollaboraOnline/online/releases/download/for-code-assets/core-co-24.04-assets.tar.gz ENV BUILDDIR /build -ENV ONLINE_EXTRA_BUILD_OPTIONS --enable-experimental +ENV ONLINE_EXTRA_BUILD_OPTIONS --enable-experimental --disable-werror +ENV COLLABORA_ONLINE_REPO https://github.com/Rash419/online.git +ENV COLLABORA_ONLINE_BRANCH live-cluster-upgrading WORKDIR /build diff --git a/docker/from-source-gh-action/build.sh b/docker/from-source-gh-action/build.sh index 8bea53f7d768e..6d838a03fa70a 100755 --- a/docker/from-source-gh-action/build.sh +++ b/docker/from-source-gh-action/build.sh @@ -74,7 +74,7 @@ fi # Clone online repo if test ! -d online ; then - git clone --depth=1 "$COLLABORA_ONLINE_REPO" online || exit 1 + git clone "$COLLABORA_ONLINE_REPO" online || exit 1 fi ( cd online && git fetch --all && git checkout -f $COLLABORA_ONLINE_BRANCH && git clean -f -d && git pull -r ) || exit 1 diff --git a/wsd/Admin.cpp b/wsd/Admin.cpp index c6a2586ec044c..841cdb5b53417 100644 --- a/wsd/Admin.cpp +++ b/wsd/Admin.cpp @@ -9,10 +9,14 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ +#include +#include #include #include +#include #include +#include #include #include @@ -41,7 +45,6 @@ using namespace COOLProtocol; -using Poco::Net::HTTPResponse; using Poco::Util::Application; const int Admin::MinStatsIntervalMs = 50; @@ -418,6 +421,10 @@ void AdminSocketHandler::handleMessage(const std::vector &payload) { _admin->setCloseMonitorFlag(); } + else if (tokens.equals(0, "rollingupdate") && tokens.size() > 1) + { + _admin->setRollingUpdateInfo(tokens[1]); + } } AdminSocketHandler::AdminSocketHandler(Admin* adminManager, @@ -1307,6 +1314,42 @@ void Admin::deleteMonitorSocket(const std::string& uriWithoutParam) } } +void Admin::setRollingUpdateInfo(const std::string& jsonString) +{ + Poco::JSON::Object::Ptr object; + if (JsonUtil::parseJSON(jsonString, object)) + { + bool status = JsonUtil::getJSONValue(object, "inprogress"); + setRollingUpdateStatus(status); + Poco::JSON::Array::Ptr infoArray = object->getArray("serverinfo"); + if (!infoArray.isNull()) + { + for(size_t i=0; i < infoArray->size(); i++) + { + if (!infoArray->isObject(i)) + { + return; + } + const auto serverInfoObject = infoArray->getObject(i); + const std::string gitHash = JsonUtil::getJSONValue(serverInfoObject , "gitHash"); + const std::string serverId = JsonUtil::getJSONValue(serverInfoObject, "serverId"); + const std::string routeToken = JsonUtil::getJSONValue(serverInfoObject, "routeToken"); + _rollingUpdateInfo.try_emplace(gitHash, RollingUpdateServerInfo(gitHash, serverId, routeToken)); + } + } + } +} + +std::string Admin::getBuddyServer(const std::string& gitHash) +{ + auto iterator = _rollingUpdateInfo.find(gitHash); + if (iterator != _rollingUpdateInfo.end()) + { + return iterator->second.getRouteToken(); + } + return std::string(); +} + void Admin::stop() { joinThread(); diff --git a/wsd/Admin.hpp b/wsd/Admin.hpp index 3b5e93725727c..679e3c4229216 100644 --- a/wsd/Admin.hpp +++ b/wsd/Admin.hpp @@ -15,6 +15,8 @@ #include "net/WebSocketHandler.hpp" #include "COOLWSD.hpp" +#include +#include class Admin; @@ -187,6 +189,14 @@ class Admin : public SocketPoll void setCloseMonitorFlag() { _closeMonitor = true; } + void setRollingUpdateInfo(const std::string& jsonString); + + void setRollingUpdateStatus(bool status) { _rollingUpdateStatus = status; } + + bool getRollingUpdateStatus() { return _rollingUpdateStatus; } + + std::string getBuddyServer(const std::string& gitHash); + private: /// Notify Forkit of changed settings. void notifyForkit(); @@ -254,6 +264,30 @@ class Admin : public SocketPoll std::map> _monitorSockets; std::atomic _closeMonitor = false; + + class RollingUpdateServerInfo + { + public: + std::string getGitHash() { return _gitHash; } + std::string getServerId() { return _serverId; } + std::string getRouteToken() { return _routeToken; } + + RollingUpdateServerInfo(const std::string& gitHash, const std::string& serverId, + const std::string& routeToken) + : _gitHash(gitHash) + , _serverId(serverId) + , _routeToken(routeToken) + { + } + + private: + std::string _gitHash; + std::string _serverId; + std::string _routeToken; + }; + + std::map _rollingUpdateInfo; + std::atomic _rollingUpdateStatus; }; /* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/wsd/ClientRequestDispatcher.cpp b/wsd/ClientRequestDispatcher.cpp index c64e1195c9fb1..85b33dcd6c9d8 100644 --- a/wsd/ClientRequestDispatcher.cpp +++ b/wsd/ClientRequestDispatcher.cpp @@ -9,7 +9,9 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ +#include "Log.hpp" #include +#include #include @@ -717,18 +719,30 @@ void ClientRequestDispatcher::handleIncomingMessage(SocketDisposition& dispositi { bool served = false; + std::string protocol = "http"; + if (socket->sniffSSL()) + protocol = "https"; + + Poco::URI requestUri(protocol + "://" + request.getHost() + request.getURI()); + const std::string& path = requestUri.getPath(); + bool versionMismatch = false; + if (path.find("browser/" COOLWSD_VERSION_HASH "/") == std::string::npos && + path.find("admin/") == std::string::npos) + { + versionMismatch = true; + } + // File server assert(socket && "Must have a valid socket"); constexpr auto ProxyRemote = "/remote/"; constexpr auto ProxyRemoteLen = sizeof(ProxyRemote) - 1; constexpr auto ProxyRemoteStatic = "/remote/static/"; - const auto uri = requestDetails.getURI(); - const auto pos = uri.find(ProxyRemoteStatic); + const auto pos = path.find(ProxyRemoteStatic); if (pos != std::string::npos) { - if (uri.ends_with("lokit-extra-img.svg")) + if (path.ends_with("lokit-extra-img.svg")) { - ProxyRequestHandler::handleRequest(uri.substr(pos + ProxyRemoteLen), socket, + ProxyRequestHandler::handleRequest(path.substr(pos + ProxyRemoteLen), socket, ProxyRequestHandler::getProxyRatingServer()); served = true; } @@ -742,12 +756,42 @@ void ClientRequestDispatcher::handleIncomingMessage(SocketDisposition& dispositi const std::string& serverUri = unlockImageUri.getScheme() + "://" + unlockImageUri.getAuthority(); ProxyRequestHandler::handleRequest( - uri.substr(pos + sizeof("/remote/static") - 1), socket, serverUri); + path.substr(pos + sizeof("/remote/static") - 1), socket, serverUri); served = true; } } #endif } + else if (COOLWSD::IndirectionServerEnabled && versionMismatch && + Admin::instance().getRollingUpdateStatus()) + { + std::string searchString = "/browser/"; + size_t startHashPos = path.find(searchString); + if (startHashPos != std::string::npos) + { + startHashPos += searchString.length(); + size_t endHashPos = path.find('/', startHashPos); + + std::string gitHash; + if (endHashPos != std::string::npos) + { + gitHash = path.substr(startHashPos, endHashPos - startHashPos); + } + else + { + gitHash = path.substr(startHashPos); + } + std::string routeToken = Admin::instance().getBuddyServer(gitHash); + LOG_DBG("Adding routeToken[" << routeToken << "] as a parameter to requestUri[" + << requestUri.toString() << ']'); + if (!routeToken.empty()) + requestUri.addQueryParameter("RouteToken", routeToken); + + ProxyRequestHandler::handleRequest(requestUri.getPathAndQuery(), socket, + requestUri.getScheme() + "://" + + requestUri.getAuthority()); + } + } else { FileServerRequestHandler::ResourceAccessDetails accessDetails; diff --git a/wsd/ProxyRequestHandler.cpp b/wsd/ProxyRequestHandler.cpp index c210cb1526009..376cc9b7c0423 100644 --- a/wsd/ProxyRequestHandler.cpp +++ b/wsd/ProxyRequestHandler.cpp @@ -43,9 +43,12 @@ void ProxyRequestHandler::handleRequest(const std::string& relPath, return; } - uriProxy.setPath(relPath); - auto sessionProxy = http::Session::create(uriProxy.getHost(), - http::Session::Protocol::HttpSsl, + uriProxy.setPathEtc(relPath); + LOG_DBG("uriProxy[" << uriProxy.getPathAndQuery() << ']'); + auto protocol = uriProxy.getScheme() == "https" ? http::Session::Protocol::HttpSsl + : http::Session::Protocol::HttpUnencrypted; + + auto sessionProxy = http::Session::create(uriProxy.getHost(), protocol, uriProxy.getPort()); sessionProxy->setTimeout(std::chrono::seconds(10)); http::Request requestProxy(uriProxy.getPathAndQuery()); diff --git a/wsd/ProxyRequestHandler.hpp b/wsd/ProxyRequestHandler.hpp index 100531a1e2e14..c810a61b2fc49 100644 --- a/wsd/ProxyRequestHandler.hpp +++ b/wsd/ProxyRequestHandler.hpp @@ -11,6 +11,7 @@ #pragma once +#include #include #include "Socket.hpp" @@ -20,6 +21,7 @@ class ProxyRequestHandler static void handleRequest(const std::string& relPath, const std::shared_ptr& socket, const std::string& serverUri); + static std::string getProxyRatingServer() { return ProxyRatingServer; } private: