You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
Modelbahn/server/session.cc

813 lines
19 KiB

#include "modelbahn.h"
#include <list>
int next_sessionID = 1;
int Session::SendData(UNIX *u, string data) {
return 0;
};
Session::Session(int rid) {
mtxchanges = { 0 };
mtxchanges = PTHREAD_MUTEX_INITIALIZER;
sessionID = random();
randomID = rid;
changes.clear();
};
Session::~Session() {
changes.clear();
};
////////////////////////////////////////////////////////////////
//
// process data and send result back
// it will process the command, and reply with all known
// changes.
//
int Session::ProcessData(JSONParse *jin, JSONParse *jout) {
JSONElement je;
JSONParse json;
JSONParse jsondata;
string command;
list<JSONElement> elements;
list<JSONElement>::iterator iter;
jout->Clear();
// debug (0, "* Session sid:%d rid:%d", sessionID, randomID);
//
// found command
if (jin->GetValue("command", &command) == 1) {
//
// editing elements
//
debug (0, "%s:%d JIN:%s", __FILE__, __LINE__, jin->ToString().c_str());
if (command.compare("addrailway") == 0) {
debug (0, "* Session Add Railways");
AddJSONRailway(jin);
}
else if (command.compare("delrailway") == 0) {
debug (0, "* Session Del Railways");
DelJSONRailway(jin);
}
else if (command.compare("addinterface") == 0) {
debug (0, "* Session Add Interface");
AddJSONInterface(jin);
}
else if (command.compare("delinterface") == 0) {
debug (0, "* Session Del Interface");
DelJSONInterface(jin);
}
//
// turnouts
//
else if (command.compare("addsensor") == 0) {
debug (0, "* Session Add Sensor");
AddJSONSensor(jin);
}
else if (command.compare("delsensor") == 0) {
debug (0, "* Session del Sensor");
DelJSONSensor(jin);
}
else if (command.compare("sensorSetActive") == 0) {
debug (0, "* Session Sensor Set Active");
printf ("%s:%d jin:%s", __FILE__, __LINE__, jin->ToString().c_str());
SetJSONSensorActive(jin);
}
//
// turnouts
//
else if (command.compare("addturnout") == 0) {
debug (0, "* Session Add Turnout");
AddJSONTurnout(jin);
}
else if (command.compare("delturnout") == 0) {
debug (0, "* Session Del Turnout");
DelJSONTurnout(jin);
}
else if (command.compare("setturnout") == 0) {
SetJSONTurnout(jin);
}
//
// Blocks
//
else if (command.compare("addblock") == 0) {
debug (0, "* Session Add Block");
AddJSONBlock(jin);
}
else if (command.compare("delblock") == 0) {
debug (0, "* Session Del Block");
DelJSONBlock(jin);
}
else if (command.compare("blockoff") == 0) {
BlockJSONOff(jin);
}
else if (command.compare("blockclear") == 0) {
BlockJSONClear(jin);
}
//
// Locomotive
//
else if (command.compare("addlocomotive") == 0) {
debug (0, "* Session Add Locomotive");
AddJSONLocomotive(jin);
}
else if (command.compare("dellocomotive") == 0) {
debug (0, "* Session Del Locomotive");
DelJSONLocomotive(jin);
}
else if (command.compare("setlocomotive") == 0) {
SetJSONLocomotive(jin);
}
else if (command.compare("locomotivedestination") == 0) {
SetJSONLocoDest(jin);
}
else if (command.compare("locomotiveassign") == 0) {
SetJSONLocoAssign(jin);
}
else if (command.compare("locomotivesetman") == 0) {
SetJSONLocoMan(jin);
}
else if (command.compare("locomotivesetauto") == 0) {
SetJSONLocoAuto(jin);
}
else if (command.compare("locomotivesetautoman") == 0) {
SetJSONLocoAutoMan(jin);
}
else if (command.compare("locomotivesetautorand") == 0) {
SetJSONLocoAutoRand(jin);
}
else if (command.compare("locomotivesetautoshed") == 0) {
SetJSONLocoAutoShed(jin);
}
else if (command.compare("locomotivereset") == 0) {
SetJSONLocoReset(jin);
}
//
// poweron / poweroff / save and resetdata
//
else if (command.compare("poweron") == 0) {
debug (0, "* Session Poweron");
server->PowerOnOff(1);
}
else if (command.compare("poweroff") == 0) {
debug (0, "* Session Poweroff");
server->PowerOnOff(0);
}
else if (command.compare("save") == 0) {
debug (0, "* Save All");
server->Save();
}
else if (command.compare("serverreset") == 0) {
debug (0, "* Server Set to Reset");
server->SetModeReset();
}
else if (command.compare("servermanual") == 0) {
debug (0, "* Server Set to Manual");
server->SetModeManual();
}
else if (command.compare("serverauto") == 0) {
debug (0, "* Server Set to Auto");
server->SetModeAuto();
}
else if (command.compare("getall") == 0) {
json.Clear();
server->GetJSONAll(&json);
// debuggin maybe we need to fix this somehow
elements = json.GetElements();
for (iter = elements.begin(); iter != elements.end(); iter++) {
// printf ("*********************** Session::ProcessData %s:%d\n\n***\n%s\n***\n", __FILE__, __LINE__, (*iter).GetString().c_str());
ChangeListPush("{"+(*iter).GetString()+"}");
}
}
else {
debug (DEBUG_ERROR | DEBUG_SESSION, "%s:%d Unknown command: '%s' JSON:%s",
__FILE__, __LINE__, command.c_str(), jin->ToString().c_str());
}
}
je = ChangeListGet();
jout->AddObject(je);
jout->AddObject("sid", sessionID);
jout->AddObject("rid", randomID);
return 1;
}
//////////////////////////////////////////////////////////////
//
// add chenges which need to be send to the clients
//
void Session::ChangeListPush(string chng) {
LockChanges();
changes.push_back(chng);
UnLockChanges();
};
//
// get the changes as json string and clear list of changes
//
JSONElement Session::ChangeListGet() {
JSONElement je;
list<string>::iterator iter;
// debug (0, "* Session::ChangeListGet cnt:%d", changes.size());
je.type = JSON_T_ARRAY;
je.name = "changes";
je.value = "[";
LockChanges();
for (iter = changes.begin(); iter != changes.end(); iter++) {
if (iter != changes.begin()) je.value += ",\n ";
else je.value += "\n ";
je.value += (*iter);
}
changes.clear();
UnLockChanges();
je.value += "]";
return je;
}
/////////////////////////////////////////////////////////////
//
// commands send from the client to the server
//
// add a new jsonrailway to the server the JSONParse Object
// will contains the full JSON string from the web page
//
void Session::AddJSONRailway(JSONParse *jp) {
int i;
JSONParse element;
JSONParse pos;
JSONParse jout;
Railway r;
list<Railway> l;
if (server == NULL) return;
server->LockThread();
for (i = 0; jp->GetObjectIdx("rail", i, &element); i++) {
debug (0, "%s:%d AddJSONRailway Element '%s'", __FILE__, __LINE__, element.ToString().c_str());
r = server->GetRailwayFromJSON(&element);
server->RailwayChange(&r);
jout.Clear();
jout.AddObject("railway", server->RailwayGetJSONRailway(r.x, r.y));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
}
//
// delete some jsonrailway from the server the JSONParse Object
// will contains the full JSON string from the web page
//
void Session::DelJSONRailway(JSONParse *jp) {
int i;
JSONParse element;
JSONParse pos;
JSONParse jout;
Railway r;
if (server == NULL) return;
server->LockThread();
for (i = 0; jp->GetObjectIdx("rail", i, &element); i++) {
debug (0, "%s:%d DelJSONRailway Element %s", __FILE__, __LINE__, element.ToString().c_str());
r = server->GetRailwayFromJSON(&element);
r.type = RAILWAY_NOTHING;
server->RailwayChange(&r);
jout.Clear();
jout.AddObject("railway", server->RailwayGetJSONRailway(r.x, r.y));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
}
//
// add new interface
//
void Session::AddJSONInterface(JSONParse *jp) {
Interface iface;
JSONParse jiface;
JSONParse jout;
server->LockThread();
jp->GetObject("interface", &jiface);
iface = server->InterfaceFromJSON(&jiface);
if (iface.name[0] != 0) {
debug (0, "%s:%d AddJSONInterface Element %s", __FILE__, __LINE__, iface.name);
// add element
server->InterfaceChange(&iface);
jout.Clear();
jout.AddObject("interface", server->InterfaceGetJSON(iface.name));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// Delete interface
//
void Session::DelJSONInterface(JSONParse *jp) {
Interface iface;
JSONParse jiface;
JSONParse jout;
string s;
server->LockThread();
jp->GetObject("interface", &jiface);
iface = server->InterfaceFromJSON(&jiface);
if (iface.name[0] != 0) {
debug (0, "%s:%d DelJSONInterface Element %s", __FILE__, __LINE__, iface.name);
// add element
server->InterfaceDelete(iface.name);
jout.Clear();
s = iface.name;
jout.AddObject("interfacedelete", s);
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// add new Sensor
//
void Session::AddJSONSensor(JSONParse *jp) {
Sensor se;
JSONParse jtmp;
JSONParse jout;
server->LockThread();
jp->GetObject("sensor", &jtmp);
se = server->SensorFromJSON(&jtmp);
if (se.name[0] != 0) {
debug (0, "%s:%d AddJSONSensor Element %s", __FILE__, __LINE__, se.name);
// add element
server->SensorChange(&se);
jout.Clear();
jout.AddObject("sensor", server->SensorGetJSON(se.name));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// Delete Sensor
//
void Session::DelJSONSensor(JSONParse *jp) {
Sensor se;
JSONParse jtmp;
JSONParse jout;
string s;
server->LockThread();
jp->GetObject("sensor", &jtmp);
se = server->SensorFromJSON(&jtmp);
if (se.name[0] != 0) {
debug (0, "%s:%d DelJSONSensor Element %s", __FILE__, __LINE__, se.name);
// add element
server->SensorDelete(se.name);
jout.Clear();
s = se.name;
jout.AddObject("sensordelete", s);
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// add new Locomotive
//
void Session::AddJSONLocomotive(JSONParse *jp) {
Locomotive loco;
JSONParse jloco;
JSONParse jout;
server->LockThread();
jp->GetObject("locomotive", &jloco);
loco = server->LocomotiveFromJSON(&jloco);
if (loco.name[0] != 0) {
debug (0, "%s:%d AddJSONLocomotive Element %s", __FILE__, __LINE__, loco.name);
// add element
server->LocomotiveChange(&loco);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco.name));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// Set Locomotive
//
void Session::SetJSONLocomotive(JSONParse *jp) {
JSONParse jloco;
JSONParse jout;
string loconame;
int speed;
int func;
int value;
server->LockThread();
jp->GetObject("locomotive", &jloco);
jloco.GetValue("name", &loconame);
if (loconame.length() > 0) {
if (jloco.GetValueInt("speed", &speed) == 1) {
//
// set speed
debug (0, "%s:%d SetJSONLocomotive Element %s Speed:%d", __FILE__, __LINE__, loconame.c_str(), speed);
server->LocomotiveSetSpeed(loconame, speed);
}
if (jloco.GetValueInt("reverse", &value) == 1) {
//
// reverse
debug (0, "%s:%d SetJSONLocomotive Element %s Reverse:%d", __FILE__, __LINE__, loconame.c_str(), value);
server->LocomotiveSetReverse(loconame, value);
}
if (jloco.GetValueInt("function", &func) == 1 && jloco.GetValueInt("value", &value) == 1) {
//
// set function
debug (0, "%s:%d SetJSONLocomotive Element %s Function:%d Value:%d", __FILE__, __LINE__, loconame.c_str(), func, value);
server->LocomotiveSetFunction(loconame, func, speed);
}
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loconame));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// Delete Locomotive
//
void Session::DelJSONLocomotive(JSONParse *jp) {
Locomotive loco;
JSONParse jloco;
JSONParse jout;
string s;
jp->GetObject("locomotive", &jloco);
loco = server->LocomotiveFromJSON(&jloco);
server->LockThread();
if (loco.name[0] != 0) {
debug (0, "%s:%d DelJSONLocomotive Element %s", __FILE__, __LINE__, loco.name);
// add element
server->LocomotiveDelete(loco.name);
jout.Clear();
s = loco.name;
jout.AddObject("locomotivedelete", s);
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
void Session::SetJSONLocoDest(JSONParse *jp) {
string loco;
string block;
int reverse;
JSONParse jout;
jp->GetValue("locomotive", &loco);
jp->GetValue("block", &block);
jp->GetValueInt("reverse", &reverse);
server->LockThread();
server->LocomotiveSetDest(loco, block, reverse);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::SetJSONLocoAssign(JSONParse *jp) {
string loco;
string block;
int reverse;
JSONParse jout;
jp->GetValue("locomotive", &loco);
jp->GetValue("block", &block);
jp->GetValueInt("reverse", &reverse);
server->LockThread();
server->LocomotiveSetAssign(loco, block, reverse);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::SetJSONLocoReset(JSONParse *jp) {
string loco;
JSONParse jout;
jp->GetValue("locomotive", &loco);
server->LockThread();
server->LocomotiveReset(loco);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::SetJSONLocoMan(JSONParse *jp) {
string loco;
JSONParse jout;
jp->GetValue("locomotive", &loco);
server->LockThread();
server->LocomotiveSetMan(loco);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::SetJSONLocoAutoMan(JSONParse *jp) {
string loco;
JSONParse jout;
jp->GetValue("locomotive", &loco);
server->LockThread();
server->LocomotiveSetAutoMan(loco);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::SetJSONLocoAuto(JSONParse *jp) {
string loco;
JSONParse jout;
jp->GetValue("locomotive", &loco);
server->LockThread();
server->LocomotiveSetAuto(loco);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::SetJSONLocoAutoRand(JSONParse *jp) {
string loco;
JSONParse jout;
jp->GetValue("locomotive", &loco);
server->LockThread();
server->LocomotiveSetAutoRand(loco);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::SetJSONLocoAutoShed(JSONParse *jp) {
string loco;
JSONParse jout;
jp->GetValue("locomotive", &loco);
server->LockThread();
server->LocomotiveSetAutoShed(loco);
jout.Clear();
jout.AddObject("locomotive", server->LocomotiveGetJSON(loco));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
//
// add new Turnout
//
void Session::AddJSONTurnout(JSONParse *jp) {
Turnout to;
JSONParse jtmp;
JSONParse jout;
server->LockThread();
jp->GetObject("turnout", &jtmp);
to = server->TurnoutFromJSON(&jtmp);
if (to.name[0] != 0) {
debug (0, "%s:%d AddJSONTurnout Element %s", __FILE__, __LINE__, to.name);
// add element
server->TurnoutChange(&to);
jout.Clear();
jout.AddObject("turnout", server->TurnoutGetJSON(to.name));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// Delete Turnout
//
void Session::DelJSONTurnout(JSONParse *jp) {
Turnout to;
JSONParse jtmp;
JSONParse jout;
string s;
server->LockThread();
jp->GetObject("turnout", &jtmp);
to = server->TurnoutFromJSON(&jtmp);
if (to.name[0] != 0) {
debug (0, "%s:%d DelJSONTurnout Element %s", __FILE__, __LINE__, to.name);
// add element
server->TurnoutDelete(to.name);
jout.Clear();
s = to.name;
jout.AddObject("turnoutdelete", s);
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// Set Turnout
//
void Session::SetJSONTurnout(JSONParse *jp) {
JSONParse jout;
string name;
string lockedby;
int active;
server->LockThread();
jp->GetValue("name", &name);
jp->GetValueInt("activate", &active);
if (name.length() > 0) {
//
// activate
debug (0, "%s:%d SetJSONTurnout Element %s active:%d", __FILE__, __LINE__, name.c_str(), active);
server->TurnoutSet(name, active);
}
server->UnLockThread();
};
//
// add new block
//
void Session::AddJSONBlock(JSONParse *jp) {
Block bl;
JSONParse jtmp;
JSONParse jout;
server->LockThread();
jp->GetObject("block", &jtmp);
bl = server->BlockFromJSON(&jtmp);
if (bl.name[0] != 0) {
debug (0, "%s:%d AddJSONBlock Element %s", __FILE__, __LINE__, bl.name);
// add element
server->BlockChange(&bl);
jout.Clear();
jout.AddObject("block", server->BlockGetJSON(bl.name));
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
//
// delete block
//
void Session::DelJSONBlock(JSONParse *jp) {
Block bl;
JSONParse jtmp;
JSONParse jout;
string s;
server->LockThread();
jp->GetObject("block", &jtmp);
bl = server->BlockFromJSON(&jtmp);
if (bl.name[0] != 0) {
debug (0, "%s:%d DelJSONBlock Element %s", __FILE__, __LINE__, bl.name);
// add element
server->BlockDelete(bl.name);
jout.Clear();
s = bl.name;
jout.AddObject("blockdelete", s);
if (network) network->ChangeListPushToAll(jout.ToString());
}
server->UnLockThread();
};
void Session::BlockJSONOff(JSONParse *jp) {
string name;
JSONParse jout;
jp->GetValue("block", &name);
server->LockThread();
server->BlockSetOff(name);
jout.Clear();
jout.AddObject("block", server->BlockGetJSON(name));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
void Session::BlockJSONClear(JSONParse *jp) {
string name;
JSONParse jout;
jp->GetValue("block", &name);
server->LockThread();
server->BlockClear(name);
jout.Clear();
jout.AddObject("block", server->BlockGetJSON(name));
if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
//
// add new block
//
void Session::SetJSONSensorActive(JSONParse *jp) {
string name;
int enabled;
JSONParse jtmp;
JSONParse jout;
server->LockThread();
jp->GetValue("sensor", &name);
jp->GetValueInt("enabled", &enabled);
server->SensorSetActive(name, enabled);
// jout.Clear();
// jout.AddObject("block", server->BlockGetJSON(bl.name));
// if (network) network->ChangeListPushToAll(jout.ToString());
server->UnLockThread();
};
/*
res = json.GetValue("command", &value);
if (res && value.compare("addelemens") == 0) {
for (i = 0; json.GetObjectIdx("elements", i, &jelement) != 0; i++) {
s = "";
jelement.GetValue("type", &s);
// printf ("i:%d t:'%s'\n", i, s.c_str());
}
}
snprintf (bufferout, BUFFERSIZE, "{\"success\":1,\"sid\":123}");
client->Write(bufferout, strlen(bufferout));
debug (0, "* write:\n%s\n* %d bytes", bufferout, strlen(bufferout));
result = 1;
*/