mirror of
https://github.com/outbackdingo/sysadm.git
synced 2026-01-27 10:20:26 +00:00
Merge remote-tracking branch 'upstream/master'
This commit is contained in:
8
.gitignore
vendored
8
.gitignore
vendored
@@ -11,6 +11,9 @@ src/library/libsysadm.so.1.0.0
|
||||
src/library/sysadm-general.o
|
||||
src/library/sysadm-lifepreserver.o
|
||||
src/library/sysadm-network.o
|
||||
src/library/sysadm-firewall.o
|
||||
src/library/sysadm-update.o
|
||||
src/library/sysadm-usermanager.o
|
||||
src/server/AuthorizationManager.o
|
||||
src/server/Makefile
|
||||
src/server/WebBackend.o
|
||||
@@ -28,4 +31,9 @@ src/server/moc_syscache-client.cpp
|
||||
src/server/moc_syscache-client.o
|
||||
src/server/sysadm-server
|
||||
src/server/syscache-client.o
|
||||
src/server/EventWatcher.o
|
||||
src/server/moc_EventWatcher.cpp
|
||||
src/server/moc_EventWatcher.o
|
||||
src/server/moc_SslServer.cpp
|
||||
src/server/moc_SslServer.o
|
||||
|
||||
|
||||
@@ -4,27 +4,29 @@ QT += core network
|
||||
TARGET=sysadm
|
||||
target.path = /usr/local/lib
|
||||
|
||||
DESTDIR= $$_PRO_FILE_PWD_
|
||||
#DESTDIR= $$_PRO_FILE_PWD_
|
||||
|
||||
TEMPLATE = lib
|
||||
LANGUAGE = C++
|
||||
VERSION = 1.0.0
|
||||
|
||||
HEADERS += sysadm-global.h \
|
||||
sysadm-general.h \
|
||||
sysadm-lifepreserver.h \
|
||||
HEADERS += sysadm-global.h \
|
||||
sysadm-general.h \
|
||||
sysadm-lifepreserver.h \
|
||||
sysadm-network.h \
|
||||
sysadm-firewall.h \
|
||||
sysadm-usermanager.h \
|
||||
sysadm-servicemanager.h
|
||||
sysadm-firewall.h \
|
||||
sysadm-servicemanager.h\
|
||||
sysadm-update.h \
|
||||
sysadm-usermanager.h
|
||||
|
||||
SOURCES += sysadm-general.cpp \
|
||||
sysadm-lifepreserver.cpp \
|
||||
sysadm-network.cpp \
|
||||
NetDevice.cpp \
|
||||
sysadm-firewall.cpp \
|
||||
sysadm-usermanager.cpp \
|
||||
sysadm-servicemanager.cpp
|
||||
SOURCES += NetDevice.cpp \
|
||||
sysadm-general.cpp \
|
||||
sysadm-lifepreserver.cpp \
|
||||
sysadm-network.cpp \
|
||||
sysadm-firewall.cpp \
|
||||
sysadm-servicemanager.cpp \
|
||||
sysadm-update.cpp \
|
||||
sysadm-usermanager.cpp
|
||||
|
||||
include.path=/usr/local/include/
|
||||
include.files=sysadm-*.h
|
||||
|
||||
@@ -8,15 +8,17 @@
|
||||
#define __PCBSD_LIB_UTILS_GENERAL_INCLUDES_H
|
||||
|
||||
//Qt Includes
|
||||
#include <QProcess>
|
||||
#include <QCoreApplication>
|
||||
#include <QFile>
|
||||
#include <QTextStream>
|
||||
#include <QDateTime>
|
||||
#include <QDir>
|
||||
#include <QDebug>
|
||||
#include <QFile>
|
||||
#include <QJsonObject>
|
||||
#include <QJsonValue>
|
||||
#include <QProcess>
|
||||
#include <QString>
|
||||
#include <QStringList>
|
||||
#include <QDateTime>
|
||||
#include <QDebug>
|
||||
#include <QTextStream>
|
||||
|
||||
//FreeBSD Includes
|
||||
#include <sys/types.h>
|
||||
|
||||
@@ -8,8 +8,6 @@
|
||||
#include "sysadm-lifepreserver.h"
|
||||
#include "sysadm-global.h"
|
||||
|
||||
#include "QJsonValue"
|
||||
|
||||
using namespace sysadm;
|
||||
|
||||
//PLEASE: Keep the functions in the same order as listed in pcbsd-general.h
|
||||
|
||||
70
src/library/sysadm-update.cpp
Normal file
70
src/library/sysadm-update.cpp
Normal file
@@ -0,0 +1,70 @@
|
||||
//===========================================
|
||||
// PC-BSD source code
|
||||
// Copyright (c) 2015, PC-BSD Software/iXsystems
|
||||
// Available under the 3-clause BSD license
|
||||
// See the LICENSE file for full details
|
||||
//===========================================
|
||||
#include "sysadm-general.h"
|
||||
#include "sysadm-update.h"
|
||||
#include "sysadm-global.h"
|
||||
|
||||
using namespace sysadm;
|
||||
|
||||
//PLEASE: Keep the functions in the same order as listed in pcbsd-general.h
|
||||
|
||||
// Return a list of updates available
|
||||
QJsonObject Update::checkUpdates() {
|
||||
QJsonObject retObject;
|
||||
|
||||
QStringList output = General::RunCommand("pc-updatemanager check").split("\n");
|
||||
QString nameval;
|
||||
|
||||
for ( int i = 0; i < output.size(); i++)
|
||||
{
|
||||
if ( output.at(i).indexOf("Your system is up to date!") != -1 )
|
||||
{
|
||||
retObject.insert("status", "noupdates");
|
||||
return retObject;
|
||||
}
|
||||
if ( output.at(i).indexOf("NAME: ") != -1 )
|
||||
nameval = output.at(i).section(" ", 1, 1);
|
||||
|
||||
if ( output.at(i).indexOf("TYPE: SECURITYUPDATE") != -1 ) {
|
||||
QJsonObject itemvals;
|
||||
itemvals.insert("name", nameval);
|
||||
retObject.insert("security", itemvals);
|
||||
}
|
||||
if ( output.at(i).indexOf("TYPE: SYSTEMUPDATE") != -1 ) {
|
||||
QJsonObject itemvals;
|
||||
itemvals.insert("name", nameval);
|
||||
if ( output.size() > ( i + 1) )
|
||||
itemvals.insert("tag", output.at(i+1).section(" ", 1, 1));
|
||||
if ( output.size() > ( i + 2) )
|
||||
itemvals.insert("version", output.at(i+2).section(" ", 1, 1));
|
||||
retObject.insert("majorupgrade", itemvals);
|
||||
}
|
||||
if ( output.at(i).indexOf("TYPE: PATCH") != -1 ) {
|
||||
QJsonObject itemvals;
|
||||
itemvals.insert("name", nameval);
|
||||
if ( output.size() > ( i + 1) )
|
||||
itemvals.insert("tag", output.at(i+1).section(" ", 1, 1));
|
||||
if ( output.size() > ( i + 2) )
|
||||
itemvals.insert("details", output.at(i+2).section(" ", 1, 1));
|
||||
if ( output.size() > ( i + 3) )
|
||||
itemvals.insert("date", output.at(i+3).section(" ", 1, 1));
|
||||
if ( output.size() > ( i + 4) )
|
||||
itemvals.insert("size", output.at(i+4).section(" ", 1, 1));
|
||||
retObject.insert("patch", itemvals);
|
||||
}
|
||||
if ( output.at(i).indexOf("TYPE: PKGUPDATE") != -1 ) {
|
||||
QJsonObject itemvals;
|
||||
itemvals.insert("name", nameval);
|
||||
retObject.insert("packageupdate", itemvals);
|
||||
}
|
||||
}
|
||||
|
||||
// Update status that we have updates
|
||||
retObject.insert("status", "updatesavailable");
|
||||
|
||||
return retObject;
|
||||
}
|
||||
22
src/library/sysadm-update.h
Normal file
22
src/library/sysadm-update.h
Normal file
@@ -0,0 +1,22 @@
|
||||
//===========================================
|
||||
// PC-BSD source code
|
||||
// Copyright (c) 2015, PC-BSD Software/iXsystems
|
||||
// Available under the 3-clause BSD license
|
||||
// See the LICENSE file for full details
|
||||
//===========================================
|
||||
#ifndef __PCBSD_LIB_UTILS_UPDATER_H
|
||||
#define __PCBSD_LIB_UTILS_UPDATER_H
|
||||
|
||||
#include <QJsonObject>
|
||||
#include "sysadm-global.h"
|
||||
|
||||
namespace sysadm{
|
||||
|
||||
class Update{
|
||||
public:
|
||||
static QJsonObject checkUpdates();
|
||||
};
|
||||
|
||||
} //end of pcbsd namespace
|
||||
|
||||
#endif
|
||||
@@ -49,6 +49,7 @@ sysadm_start()
|
||||
ssl_keygen
|
||||
echo "Starting sysadm (REST)..."
|
||||
daemon -p /var/run/sysadm-rest.pid $command $flags >/dev/null 2>/dev/null
|
||||
chmod 744 /var/run/sysadm-rest.pid >/dev/null 2>/dev/null
|
||||
}
|
||||
|
||||
run_rc_command "$1"
|
||||
|
||||
@@ -49,6 +49,7 @@ sysadm_start()
|
||||
ssl_keygen
|
||||
echo "Starting sysadm (WebSocket)..."
|
||||
daemon -p /var/run/sysadm-websocket.pid $command $flags >/dev/null 2>/dev/null
|
||||
chmod 744 /var/run/sysadm-websocket.pid >/dev/null 2>/dev/null
|
||||
}
|
||||
|
||||
run_rc_command "$1"
|
||||
|
||||
@@ -25,7 +25,13 @@ void EventWatcher::start(){
|
||||
WatcherUpdate(DISPATCHWORKING); //load it initially
|
||||
}
|
||||
|
||||
QString EventWatcher::lastEvent(EVENT_TYPE type){
|
||||
EventWatcher::EVENT_TYPE EventWatcher::typeFromString(QString typ){
|
||||
if(typ=="dispatcher"){ return DISPATCHER; }
|
||||
else if(typ=="life-preserver"){ return LIFEPRESERVER; }
|
||||
else{ return BADEVENT; }
|
||||
}
|
||||
|
||||
QJsonValue EventWatcher::lastEvent(EVENT_TYPE type){
|
||||
if(HASH.contains(type)){ return HASH.value(type); }
|
||||
else{ return ""; }
|
||||
}
|
||||
@@ -50,7 +56,16 @@ void EventWatcher::WatcherUpdate(QString path){
|
||||
qDebug() << "Dispatcher Update:" << stat;
|
||||
HASH.insert(DISPATCHER,stat); //save for later
|
||||
//Forward those contents on to the currently-open sockets
|
||||
emit NewEvent(DISPATCHER, stat);
|
||||
emit NewEvent(DISPATCHER, QJsonValue(stat) );
|
||||
}else if(path==LPLOG){
|
||||
//Main Life Preserver Log File
|
||||
|
||||
}else if(path==LPERRLOG){
|
||||
//Life Preserver Error log
|
||||
|
||||
}else if(path==tmpLPRepFile){
|
||||
//Life Preserver Replication Log (currently-running replication)
|
||||
|
||||
}
|
||||
|
||||
//Make sure this file/dir is not removed from the watcher
|
||||
|
||||
@@ -9,23 +9,33 @@
|
||||
#include "globals-qt.h"
|
||||
|
||||
#define DISPATCHWORKING QString("/var/tmp/appcafe/dispatch-queue.working")
|
||||
#define LPLOG QString("/var/log/lpreserver/lpreserver.log")
|
||||
#define LPERRLOG QString("/var/log/lpreserver/error.log")
|
||||
#define LPREPLOGDIR QString("/var/log/lpreserver/")
|
||||
|
||||
class EventWatcher : public QObject{
|
||||
Q_OBJECT
|
||||
public:
|
||||
//Add more event types here as needed
|
||||
enum EVENT_TYPE{ DISPATCHER };
|
||||
enum EVENT_TYPE{ BADEVENT, DISPATCHER, LIFEPRESERVER};
|
||||
|
||||
EventWatcher();
|
||||
~EventWatcher();
|
||||
|
||||
void start();
|
||||
|
||||
QString lastEvent(EVENT_TYPE type);
|
||||
//Convert a string into the type flag
|
||||
static EVENT_TYPE typeFromString(QString);
|
||||
|
||||
//Retrieve the most recent event message for a particular type of event
|
||||
QJsonValue lastEvent(EVENT_TYPE type);
|
||||
|
||||
private:
|
||||
QFileSystemWatcher *watcher;
|
||||
QHash<EVENT_TYPE, QString> HASH;
|
||||
QHash<unsigned int, QJsonValue> HASH;
|
||||
//HASH Note: Fields 1-99 reserved for EVENT_TYPE enum (last message of that type)
|
||||
// Fields 100-199 reserved for Life Preserver logs (all types)
|
||||
QString tmpLPRepFile;
|
||||
|
||||
QString readFile(QString path);
|
||||
|
||||
@@ -36,6 +46,6 @@ private slots:
|
||||
void WatcherUpdate(QString);
|
||||
|
||||
signals:
|
||||
void NewEvent(EVENT_TYPE ev, QString msg); //type/message
|
||||
void NewEvent(EventWatcher::EVENT_TYPE, QJsonValue); //type/message
|
||||
};
|
||||
#endif
|
||||
|
||||
@@ -5,12 +5,7 @@
|
||||
// =================================
|
||||
#ifndef _PCBSD_REST_SERVER_REST_STRUCTS_H
|
||||
#define _PCBSD_REST_SERVER_REST_STRUCTS_H
|
||||
#include <QString>
|
||||
#include <QStringList>
|
||||
#include <QDateTime>
|
||||
#include <QJsonValue>
|
||||
#include <QJsonDocument>
|
||||
#include <QJsonObject>
|
||||
#include "globals-qt.h"
|
||||
|
||||
#define CurHttpVersion QString("HTTP/1.1")
|
||||
|
||||
@@ -33,13 +28,16 @@ public:
|
||||
//Raw Text
|
||||
QStringList Header; //REST Headers
|
||||
QString Body; //Everything else
|
||||
//User Permissions level
|
||||
bool fullaccess;
|
||||
|
||||
RestInputStruct(QString message = ""){
|
||||
HTTPVERSION = CurHttpVersion; //default value
|
||||
fullaccess = false;
|
||||
if(message.isEmpty()){ return; }
|
||||
//Pull out any REST headers
|
||||
Body = message;
|
||||
qDebug() << "Raw Message:" << message;
|
||||
//qDebug() << "Raw Message:" << message;
|
||||
if(!message.startsWith("{")){
|
||||
Header = message.section("{",0,0).split("\n");
|
||||
Body = "{"+message.section("{",1, 1000000);
|
||||
|
||||
@@ -10,15 +10,16 @@
|
||||
|
||||
//sysadm library interface classes
|
||||
#include "sysadm-general.h"
|
||||
#include "sysadm-network.h"
|
||||
#include "sysadm-lifepreserver.h"
|
||||
#include "sysadm-network.h"
|
||||
#include "sysadm-update.h"
|
||||
|
||||
#include "syscache-client.h"
|
||||
#include "dispatcher-client.h"
|
||||
|
||||
#define DEBUG 0
|
||||
#define SCLISTDELIM QString("::::") //SysCache List Delimiter
|
||||
RestOutputStruct::ExitCode WebSocket::AvailableSubsystems(QJsonObject *out){
|
||||
RestOutputStruct::ExitCode WebSocket::AvailableSubsystems(bool allaccess, QJsonObject *out){
|
||||
//Probe the various subsystems to see what is available through this server
|
||||
//Output format:
|
||||
/*<out>{
|
||||
@@ -26,7 +27,7 @@ RestOutputStruct::ExitCode WebSocket::AvailableSubsystems(QJsonObject *out){
|
||||
<namespace2/name2> : <read/write/other>,
|
||||
}
|
||||
*/
|
||||
bool allaccess = AUTHSYSTEM->hasFullAccess(SockAuthToken);
|
||||
//bool allaccess = AUTHSYSTEM->hasFullAccess(SockAuthToken);
|
||||
// - syscache
|
||||
if(QFile::exists("/var/run/syscache.pipe")){
|
||||
out->insert("rpc/syscache","read"); //no write to syscache - only reads
|
||||
@@ -47,25 +48,27 @@ RestOutputStruct::ExitCode WebSocket::AvailableSubsystems(QJsonObject *out){
|
||||
return RestOutputStruct::OK;
|
||||
}
|
||||
|
||||
RestOutputStruct::ExitCode WebSocket::EvaluateBackendRequest(QString namesp, QString name, const QJsonValue args, QJsonObject *out){
|
||||
RestOutputStruct::ExitCode WebSocket::EvaluateBackendRequest(const RestInputStruct &IN, QJsonObject *out){
|
||||
/*Inputs:
|
||||
"namesp" - namespace for the request
|
||||
"name" - name of the request
|
||||
"args" - JSON input arguments structure
|
||||
"out" - JSON output arguments structure
|
||||
*/
|
||||
namesp = namesp.toLower(); name = name.toLower();
|
||||
QString namesp = IN.namesp.toLower(); QString name = IN.name.toLower();
|
||||
//Go through and forward this request to the appropriate sub-system
|
||||
if(namesp=="rpc" && name=="query"){
|
||||
return AvailableSubsystems(out);
|
||||
return AvailableSubsystems(IN.fullaccess, out);
|
||||
}else if(namesp=="rpc" && name=="syscache"){
|
||||
return EvaluateSyscacheRequest(args, out);
|
||||
return EvaluateSyscacheRequest(IN.args, out);
|
||||
}else if(namesp=="rpc" && name=="dispatcher"){
|
||||
return EvaluateDispatcherRequest(args, out);
|
||||
return EvaluateDispatcherRequest(IN.args, out);
|
||||
}else if(namesp=="sysadm" && name=="network"){
|
||||
return EvaluateSysadmNetworkRequest(args, out);
|
||||
return EvaluateSysadmNetworkRequest(IN.args, out);
|
||||
}else if(namesp=="sysadm" && name=="lifepreserver"){
|
||||
return EvaluateSysadmLifePreserverRequest(args, out);
|
||||
return EvaluateSysadmLifePreserverRequest(IN.args, out);
|
||||
}else if(namesp=="sysadm" && name=="update"){
|
||||
return EvaluateSysadmUpdateRequest(IN.args, out);
|
||||
}else{
|
||||
return RestOutputStruct::BADREQUEST;
|
||||
}
|
||||
@@ -241,3 +244,29 @@ RestOutputStruct::ExitCode WebSocket::EvaluateSysadmLifePreserverRequest(const Q
|
||||
}
|
||||
return RestOutputStruct::OK;
|
||||
}
|
||||
|
||||
//==== SYSADM -- Update ====
|
||||
RestOutputStruct::ExitCode WebSocket::EvaluateSysadmUpdateRequest(const QJsonValue in_args, QJsonObject *out){
|
||||
if(in_args.isObject()){
|
||||
QStringList keys = in_args.toObject().keys();
|
||||
bool ok = false;
|
||||
if(keys.contains("action")){
|
||||
QString act = JsonValueToString(in_args.toObject().value("action"));
|
||||
if(act=="checkupdates"){
|
||||
ok = true;
|
||||
qDebug() << " - Starting update check";
|
||||
out->insert("checkupdates", sysadm::Update::checkUpdates());
|
||||
qDebug() << " - Finished update check";
|
||||
}
|
||||
|
||||
} //end of "action" key usage
|
||||
|
||||
//If nothing done - return the proper code
|
||||
if(!ok){
|
||||
return RestOutputStruct::BADREQUEST;
|
||||
}
|
||||
}else{ // if(in_args.isArray()){
|
||||
return RestOutputStruct::BADREQUEST;
|
||||
}
|
||||
return RestOutputStruct::OK;
|
||||
}
|
||||
|
||||
@@ -15,10 +15,6 @@ WebServer::WebServer(){
|
||||
WSServer = 0;
|
||||
TCPServer = 0;
|
||||
AUTH = new AuthorizationManager();
|
||||
//watcher = new QFileSystemWatcher(this);
|
||||
|
||||
//connect(watcher, SIGNAL(fileChanged(const QString&)), this, SLOT(WatcherUpdate(QString)) );
|
||||
//connect(watcher, SIGNAL(directoryChanged(const QString&)), this, SLOT(WatcherUpdate(QString)) );
|
||||
}
|
||||
|
||||
WebServer::~WebServer(){
|
||||
@@ -124,7 +120,7 @@ void WebServer::NewSocketConnection(){
|
||||
if(sock==0){ return; } //no new connection
|
||||
qDebug() << "New Socket Connection";
|
||||
connect(sock, SIGNAL(SocketClosed(QString)), this, SLOT(SocketClosed(QString)) );
|
||||
connect(EVENTS, SIGNAL(NewEvent(EventWatcher::EVENT_TYPE, QString)), sock, SLOT(EventUpdate(EventWatcher::EVENT_TYPE, QString)) );
|
||||
connect(EVENTS, SIGNAL(NewEvent(EventWatcher::EVENT_TYPE, QJsonValue)), sock, SLOT(EventUpdate(EventWatcher::EVENT_TYPE, QJsonValue)) );
|
||||
OpenSockets << sock;
|
||||
}
|
||||
|
||||
|
||||
@@ -15,7 +15,6 @@ WebSocket::WebSocket(QWebSocket *sock, QString ID, AuthorizationManager *auth){
|
||||
SockAuthToken.clear(); //nothing set initially
|
||||
SOCKET = sock;
|
||||
TSOCKET = 0;
|
||||
SendAppCafeEvents = false;
|
||||
AUTHSYSTEM = auth;
|
||||
idletimer = new QTimer(this);
|
||||
idletimer->setInterval(IDLETIMEOUTMINS*60000); //connection timout for idle sockets
|
||||
@@ -32,7 +31,6 @@ WebSocket::WebSocket(QSslSocket *sock, QString ID, AuthorizationManager *auth){
|
||||
SockAuthToken.clear(); //nothing set initially
|
||||
TSOCKET = sock;
|
||||
SOCKET = 0;
|
||||
SendAppCafeEvents = false;
|
||||
AUTHSYSTEM = auth;
|
||||
idletimer = new QTimer(this);
|
||||
idletimer->setInterval(IDLETIMEOUTMINS*60000); //connection timout for idle sockets
|
||||
@@ -50,6 +48,7 @@ WebSocket::WebSocket(QSslSocket *sock, QString ID, AuthorizationManager *auth){
|
||||
}
|
||||
|
||||
WebSocket::~WebSocket(){
|
||||
qDebug() << "SOCKET Destroyed";
|
||||
if(SOCKET!=0){
|
||||
SOCKET->close();
|
||||
delete SOCKET;
|
||||
@@ -70,8 +69,8 @@ QString WebSocket::ID(){
|
||||
//=======================
|
||||
void WebSocket::sendReply(QString msg){
|
||||
qDebug() << "Sending Socket Reply";
|
||||
if(SOCKET!=0){ SOCKET->sendTextMessage(msg); } //Websocket connection
|
||||
else if(TSOCKET!=0){
|
||||
if(SOCKET!=0 && SOCKET->isValid()){ SOCKET->sendTextMessage(msg); } //Websocket connection
|
||||
else if(TSOCKET!=0 && TSOCKET->isValid()){
|
||||
//TCP Socket connection
|
||||
TSOCKET->write(msg.toUtf8().data());
|
||||
TSOCKET->disconnectFromHost(); //TCP/REST connections are 1 connection per message.
|
||||
@@ -109,8 +108,6 @@ void WebSocket::EvaluateREST(QString msg){
|
||||
out.Header << "Accept: text/json";
|
||||
out.Header << "Content-Type: text/json; charset=utf-8";
|
||||
this->sendReply(out.assembleMessage());
|
||||
/* if(SOCKET!=0){ SOCKET->sendTextMessage(out.assembleMessage()); }
|
||||
else if(TSOCKET!=0){ TSOCKET->write(out.assembleMessage().toUtf8().data()); }*/
|
||||
}else{
|
||||
EvaluateRequest(IN);
|
||||
}
|
||||
@@ -172,9 +169,11 @@ void WebSocket::EvaluateRequest(const RestInputStruct &REQ){
|
||||
|
||||
}else if( AUTHSYSTEM->checkAuth(SockAuthToken) ){ //validate current Authentication token
|
||||
//Now provide access to the various subsystems
|
||||
// First get/set the permissions flag into the input structure
|
||||
out.in_struct.fullaccess = AUTHSYSTEM->hasFullAccess(SockAuthToken);
|
||||
//Pre-set any output fields
|
||||
QJsonObject outargs;
|
||||
out.CODE = EvaluateBackendRequest(out.in_struct.namesp, out.in_struct.name, out.in_struct.args, &outargs);
|
||||
out.CODE = EvaluateBackendRequest(out.in_struct, &outargs);
|
||||
out.out_args = outargs;
|
||||
}else{
|
||||
//Bad/No authentication
|
||||
@@ -190,21 +189,27 @@ void WebSocket::EvaluateRequest(const RestInputStruct &REQ){
|
||||
if(out.in_struct.args.isObject()){ evlist << JsonValueToString(out.in_struct.args); }
|
||||
else if(out.in_struct.args.isArray()){ evlist = JsonArrayToStringList(out.in_struct.args.toArray()); }
|
||||
//Now subscribe/unsubscribe to these events
|
||||
if(out.in_struct.name=="subscribe"){
|
||||
if(evlist.contains("dispatcher")){
|
||||
SendAppCafeEvents = true;
|
||||
outargs.insert("subscribe",QJsonValue("dispatcher"));
|
||||
QTimer::singleShot(100, this, SLOT(AppCafeStatusUpdate()) );
|
||||
}
|
||||
}else if(out.in_struct.name=="unsubscribe"){
|
||||
if(evlist.contains("dispatcher")){
|
||||
SendAppCafeEvents = false;
|
||||
outargs.insert("unsubscribe",QJsonValue("dispatcher"));
|
||||
int sub = -1; //bad input
|
||||
if(out.in_struct.name=="subscribe"){ sub = 1; }
|
||||
else if(out.in_struct.name=="unsubscribe"){ sub = 0; }
|
||||
|
||||
if(sub>=0 && !evlist.isEmpty() ){
|
||||
for(int i=0; i<evlist.length(); i++){
|
||||
EventWatcher::EVENT_TYPE type = EventWatcher::typeFromString(evlist[i]);
|
||||
if(type==EventWatcher::BADEVENT){ continue; }
|
||||
outargs.insert(out.in_struct.name,QJsonValue(evlist[i]));
|
||||
if(sub==1){
|
||||
ForwardEvents << type;
|
||||
QTimer::singleShot(100, this, SLOT(EventUpdate(type)) );
|
||||
}else{
|
||||
ForwardEvents.removeAll(type);
|
||||
}
|
||||
}
|
||||
out.out_args = outargs;
|
||||
}else{
|
||||
outargs.insert("unknown",QJsonValue("unknown"));
|
||||
//Bad/No authentication
|
||||
out.CODE = RestOutputStruct::BADREQUEST;
|
||||
}
|
||||
out.out_args = outargs;
|
||||
}else{
|
||||
//Bad/No authentication
|
||||
out.CODE = RestOutputStruct::UNAUTHORIZED;
|
||||
@@ -212,9 +217,11 @@ void WebSocket::EvaluateRequest(const RestInputStruct &REQ){
|
||||
//Other namespace - check whether auth has already been established before continuing
|
||||
}else if( AUTHSYSTEM->checkAuth(SockAuthToken) ){ //validate current Authentication token
|
||||
//Now provide access to the various subsystems
|
||||
// First get/set the permissions flag into the input structure
|
||||
out.in_struct.fullaccess = AUTHSYSTEM->hasFullAccess(SockAuthToken);
|
||||
//Pre-set any output fields
|
||||
QJsonObject outargs;
|
||||
out.CODE = EvaluateBackendRequest(out.in_struct.namesp, out.in_struct.name, out.in_struct.args, &outargs);
|
||||
out.CODE = EvaluateBackendRequest(out.in_struct, &outargs);
|
||||
out.out_args = outargs;
|
||||
}else{
|
||||
//Error in inputs - assemble the return error message
|
||||
@@ -274,10 +281,13 @@ void WebSocket::checkIdle(){
|
||||
}
|
||||
|
||||
void WebSocket::SocketClosing(){
|
||||
qDebug() << "Socket Closing...";
|
||||
qDebug() << "Socket Closing..." ;
|
||||
if(idletimer->isActive()){
|
||||
//This means the client deliberately closed the connection - not the idle timer
|
||||
qDebug() << " - Client Closed Connection";
|
||||
idletimer->stop();
|
||||
}else{
|
||||
qDebug() << "idleTimer not running";
|
||||
}
|
||||
//Stop any current requests
|
||||
|
||||
@@ -291,16 +301,16 @@ void WebSocket::SocketClosing(){
|
||||
void WebSocket::EvaluateMessage(const QByteArray &msg){
|
||||
qDebug() << "New Binary Message:";
|
||||
if(idletimer->isActive()){ idletimer->stop(); }
|
||||
EvaluateREST( QString(msg) );
|
||||
idletimer->start();
|
||||
EvaluateREST( QString(msg) );
|
||||
qDebug() << " - Done with Binary Message";
|
||||
}
|
||||
|
||||
void WebSocket::EvaluateMessage(const QString &msg){
|
||||
qDebug() << "New Text Message:";
|
||||
if(idletimer->isActive()){ idletimer->stop(); }
|
||||
EvaluateREST(msg);
|
||||
idletimer->start();
|
||||
EvaluateREST(msg);
|
||||
qDebug() << " - Done with Text Message";
|
||||
}
|
||||
|
||||
@@ -335,18 +345,21 @@ void WebSocket::SslError(const QList<QSslError> &err){ //sslErrors() signal
|
||||
// ======================
|
||||
// PUBLIC SLOTS
|
||||
// ======================
|
||||
void WebSocket::EventUpdate(EventWatcher::EVENT_TYPE evtype, QString msg){
|
||||
if(msg.isEmpty()){ msg = EVENTS->lastEvent(evtype); }
|
||||
void WebSocket::EventUpdate(EventWatcher::EVENT_TYPE evtype, QJsonValue msg){
|
||||
if(msg.isUndefined()){ msg = EVENTS->lastEvent(evtype); }
|
||||
//qDebug() << "Socket Status Update:" << msg;
|
||||
if(evtype==EventWatcher::DISPATCHER){
|
||||
if(!SendAppCafeEvents){ return; } //don't report events on this socket
|
||||
RestOutputStruct out;
|
||||
out.CODE = RestOutputStruct::OK;
|
||||
out.in_struct.name = "dispatcher";
|
||||
out.in_struct.namesp = "events";
|
||||
out.out_args = QJsonValue(msg);//outargs;
|
||||
if(!ForwardEvents.contains(evtype)){ return; }
|
||||
RestOutputStruct out;
|
||||
out.CODE = RestOutputStruct::OK;
|
||||
out.in_struct.namesp = "events";
|
||||
out.out_args = msg;
|
||||
out.Header << "Content-Type: text/json; charset=utf-8"; //REST header info
|
||||
//Now send the message back through the socket
|
||||
this->sendReply(out.assembleMessage());
|
||||
} //end of DISPATCH event
|
||||
if(evtype==EventWatcher::DISPATCHER){
|
||||
out.in_struct.name = "dispatcher";
|
||||
}else if(evtype==EventWatcher::LIFEPRESERVER){
|
||||
out.in_struct.name = "life-preserver";
|
||||
}
|
||||
|
||||
//Now send the message back through the socket
|
||||
this->sendReply(out.assembleMessage());
|
||||
}
|
||||
|
||||
@@ -26,7 +26,7 @@ private:
|
||||
QSslSocket *TSOCKET;
|
||||
QString SockID, SockAuthToken;
|
||||
AuthorizationManager *AUTHSYSTEM;
|
||||
bool SendAppCafeEvents;
|
||||
QList<EventWatcher::EVENT_TYPE> ForwardEvents;
|
||||
|
||||
void sendReply(QString msg);
|
||||
|
||||
@@ -40,9 +40,9 @@ private:
|
||||
|
||||
//Backend request/reply functions (contained in WebBackend.cpp)
|
||||
// -- Subsystem listing routine
|
||||
RestOutputStruct::ExitCode AvailableSubsystems(QJsonObject *out);
|
||||
RestOutputStruct::ExitCode AvailableSubsystems(bool fullaccess, QJsonObject *out);
|
||||
// -- Main subsystem parser
|
||||
RestOutputStruct::ExitCode EvaluateBackendRequest(QString namesp, QString name, const QJsonValue in_args, QJsonObject *out);
|
||||
RestOutputStruct::ExitCode EvaluateBackendRequest(const RestInputStruct&, QJsonObject *out);
|
||||
// -- Individual subsystems
|
||||
RestOutputStruct::ExitCode EvaluateSyscacheRequest(const QJsonValue in_args, QJsonObject *out);
|
||||
RestOutputStruct::ExitCode EvaluateDispatcherRequest(const QJsonValue in_args, QJsonObject *out);
|
||||
@@ -50,6 +50,8 @@ private:
|
||||
RestOutputStruct::ExitCode EvaluateSysadmNetworkRequest(const QJsonValue in_args, QJsonObject *out);
|
||||
// -- sysadm LifePreserver API
|
||||
RestOutputStruct::ExitCode EvaluateSysadmLifePreserverRequest(const QJsonValue in_args, QJsonObject *out);
|
||||
// -- sysadm Update API
|
||||
RestOutputStruct::ExitCode EvaluateSysadmUpdateRequest(const QJsonValue in_args, QJsonObject *out);
|
||||
|
||||
private slots:
|
||||
void checkIdle(); //see if the currently-connected client is idle
|
||||
@@ -66,7 +68,7 @@ private slots:
|
||||
void SslError(const QList<QSslError>&); //sslErrors() signal
|
||||
|
||||
public slots:
|
||||
void EventUpdate(EventWatcher::EVENT_TYPE, QString msg = "");
|
||||
void EventUpdate(EventWatcher::EVENT_TYPE, QJsonValue = QJsonValue() );
|
||||
|
||||
signals:
|
||||
void SocketClosed(QString); //ID
|
||||
|
||||
@@ -19,6 +19,7 @@
|
||||
#include <QUrl>
|
||||
#include <QFile>
|
||||
#include <QDir>
|
||||
#include <QDateTime>
|
||||
#include <QTextStream>
|
||||
#include <QProcess>
|
||||
#include <QSslKey>
|
||||
|
||||
Reference in New Issue
Block a user