5#include "serverengine.h"
8#include "localserver.h"
10#include "protocolfastcgi.h"
11#include "protocolhttp.h"
12#include "protocolhttp2.h"
13#include "protocolwebsocket.h"
18#include "tcpserverbalancer.h"
19#include "tcpsslserver.h"
25#include <Cutelyst/Application>
26#include <Cutelyst/Context>
27#include <Cutelyst/Request>
28#include <Cutelyst/Response>
32#include <QCoreApplication>
33#include <QLoggingCategory>
35Q_LOGGING_CATEGORY(C_SERVER_ENGINE,
"cutelyst.server.engine", QtWarningMsg)
39QByteArray dateHeader();
43 const QVariantMap &opts,
45 :
Engine(localApp, workerCore, opts)
48 m_lastDate = dateHeader();
49 m_lastDateTimer.start();
51 if (m_wsgi->socketTimeout()) {
52 m_socketTimeout =
new QTimer(
this);
53 m_socketTimeout->setObjectName(QStringLiteral(
"Cutelyst::socketTimeout"));
54 m_socketTimeout->setInterval(std::chrono::seconds{m_wsgi->socketTimeout()});
57 connect(
this, &ServerEngine::shutdown, app(), [
this] { Q_EMIT app()->shuttingDown(app()); });
59 const QStringList staticMap = m_wsgi->staticMap();
60 const QStringList staticMap2 = m_wsgi->staticMap2();
61 if (!staticMap.isEmpty() || !staticMap2.isEmpty()) {
63 auto staticMapPlugin =
new StaticMap(app());
65 for (
const QString &part : staticMap) {
66 staticMapPlugin->addStaticMap(
67 part.section(QLatin1Char(
'='), 0, 0), part.section(QLatin1Char(
'='), 1, 1),
false);
70 for (
const QString &part : staticMap2) {
71 staticMapPlugin->addStaticMap(
72 part.section(QLatin1Char(
'='), 0, 0), part.section(QLatin1Char(
'='), 1, 1),
true);
77ServerEngine::~ServerEngine()
89void ServerEngine::setServers(
const std::vector<QObject *> &servers)
91 for (QObject *server : servers) {
92 auto balancer = qobject_cast<TcpServerBalancer *>(server);
94 TcpServer *server = balancer->createServer(
this);
97 if (m_socketTimeout) {
99 m_socketTimeout, &QTimer::timeout, server, &TcpServer::timeoutConnections);
102 if (server->protocol()->type() == Protocol::Type::Http11) {
103 server->setProtocol(getProtoHttp());
104 }
else if (server->protocol()->type() == Protocol::Type::Http2) {
105 server->setProtocol(getProtoHttp2());
106 }
else if (server->protocol()->type() == Protocol::Type::FastCGI1) {
107 server->setProtocol(getProtoFastCgi());
111 if (m_wsgi->httpsH2()) {
112 auto sslServer = qobject_cast<TcpSslServer *>(server);
114 sslServer->setHttp2Protocol(getProtoHttp2());
121 auto localServer = qobject_cast<LocalServer *>(server);
123 LocalServer *server = localServer->createServer(
this);
126 if (m_socketTimeout) {
127 connect(m_socketTimeout,
130 &LocalServer::timeoutConnections);
133 if (server->protocol()->type() == Protocol::Type::Http11) {
134 server->setProtocol(getProtoHttp());
135 }
else if (server->protocol()->type() == Protocol::Type::Http2) {
136 server->setProtocol(getProtoHttp2());
137 }
else if (server->protocol()->type() == Protocol::Type::FastCGI1) {
138 server->setProtocol(getProtoFastCgi());
145void ServerEngine::postFork(
int workerId)
156 std::cerr <<
"Application failed to post fork, cheaping worker: " <<
workerId
162QByteArray ServerEngine::dateHeader()
165 ret = QLatin1String(
"\r\nDate: ") +
166 QLocale::c().toString(QDateTime::currentDateTimeUtc(),
167 QStringLiteral(
"ddd, dd MMM yyyy hh:mm:ss 'GMT"));
168 return ret.toLatin1();
171Protocol *ServerEngine::getProtoHttp()
174 if (m_wsgi->upgradeH2c()) {
175 m_protoHttp =
new ProtocolHttp(m_wsgi, getProtoHttp2());
191Protocol *ServerEngine::getProtoFastCgi()
208void ServerEngine::handleSocketShutdown(
Socket *socket)
210 if (socket->processing == 0) {
211 socket->connectionClose();
212 }
else if (socket->proto->type() == Protocol::Type::Http11Websocket) {
214 req->webSocketClose(Response::CloseCode::CloseCodeGoingAway, {});
216 socket->protoData->headerConnection = ProtocolData::HeaderConnection::Close;
220#include "moc_serverengine.cpp"
The Cutelyst application.
bool postForkApplication()
virtual int workerId() const override
virtual bool init() override
The Cutelyst namespace holds all public Cutelyst API.