/*
*
* ProLinga-Run
*
* Copyright (C) 2002-2008 Xobas Software.
* All rights reserved.
*
* This file is part of ProLinga-Run.
*
* ProLinga-Run is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* ProLinga-Run is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with ProLinga-Run. If not, see .
*
* More information is available at the following addresses:
*
* Website : http://www.prolinga.org
*
* Email : prolinga-list@prolinga.org
*
*
*/
#include "RunCommon.h"
#include
#include
#include "BuiltIn.hpp"
#include "RunCommand.hpp"
#include "Main.hpp"
#include "RunError.hpp"
#include "RunRunLogic.hpp"
extern BiWebParameterPtr biWebPtr;
void CreateResponse(xmlDocPtr *docResponse, xmlNodePtr *curResponse)
{
/* Set up Response file */
*docResponse = xmlNewDoc((const xmlChar *)XML_VERSION);
(*docResponse)->children = xmlNewDocNode(*docResponse, NULL, (const xmlChar *)ROOT_ELEM, NULL);
*curResponse = xmlDocGetRootElement(*docResponse);
xmlNewTextChild (*curResponse, NULL, (const xmlChar *)"Web", (const xmlChar *)"");
*curResponse = (*curResponse)->xmlChildrenNode;
xmlNewProp (*curResponse, (const xmlChar *)"Version", (const xmlChar *)RUN_DOC_VERSION);
}
void CreateCommandDoc(xmlNodePtr cur, xmlDocPtr *docCmd)
{
xmlNodePtr curCmd;
/* Set node pointer to object in repository command */
cur = cur->xmlChildrenNode;
while (cur != NULL)
{
if (!xmlStrcmp(cur->name, (const xmlChar *) "Object"))
break;
cur = cur->next;
}
/* Create new Command Doc */
*docCmd = xmlNewDoc((const xmlChar *)XML_VERSION);
(**docCmd).children = xmlNewDocNode(*docCmd, NULL, (const xmlChar *)ROOT_ELEM, NULL);
curCmd = xmlDocGetRootElement(*docCmd);
curCmd->xmlChildrenNode = xmlCopyNodeList(cur);
}
void CreateResponseCommand(const char *cmdName, const char *sessionId, const char *format, xmlDocPtr **docCmd)
{
xmlNodePtr curCmd;
/* Create Command Response */
**docCmd = xmlNewDoc((const xmlChar *)XML_VERSION);
(***docCmd).children = xmlNewDocNode(**docCmd, NULL, (const xmlChar *)ROOT_ELEM, NULL);
curCmd = xmlDocGetRootElement(**docCmd);
xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Command", (const xmlChar *)"");
curCmd = curCmd->xmlChildrenNode;
xmlNewProp (curCmd, (const xmlChar *)"Name", (const xmlChar *)cmdName);
xmlNewProp (curCmd, (const xmlChar *)"Mode", (const xmlChar *)"Response");
xmlNewProp (curCmd, (const xmlChar *)"SessionId", (const xmlChar *)sessionId);
xmlNewProp (curCmd, (const xmlChar *)"Format", (const xmlChar *)format);
}
void InsertResponseObject(const char *objSvc, const char *objAppn, const char *objName, xmlDocPtr **docCmd)
{
xmlNodePtr curCmd;
/* Insert svc, appn and name in Command Response */
curCmd = xmlDocGetRootElement(**docCmd);
if (!xmlStrcmp(curCmd->name, (const xmlChar *) "text"))
curCmd = curCmd->next;
curCmd = curCmd->xmlChildrenNode;
if (!xmlStrcmp(curCmd->name, (const xmlChar *) "text"))
curCmd = curCmd->next;
curCmd = xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Object", (const xmlChar *)"");
xmlNewProp (curCmd, (const xmlChar *)"Application", (const xmlChar *)objSvc);
xmlNewProp (curCmd, (const xmlChar *)"Type", (const xmlChar *)objAppn);
//curCmd = xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Name", (const xmlChar *)objName);
xmlNewProp (curCmd, (const xmlChar *)"Name", (const xmlChar *)objName);
}
void InsertResponseWeb(const char *objSvc, const char *objAppn, const char *objName, const xmlDocPtr docRespWeb, xmlDocPtr **docCmd)
{
xmlNodePtr curCmd, curRespWeb;
/* Insert svc, appn and name in Command Response */
curCmd = xmlDocGetRootElement(**docCmd);
if (!xmlStrcmp(curCmd->name, (const xmlChar *) "text"))
curCmd = curCmd->next;
curCmd = curCmd->xmlChildrenNode;
if (!xmlStrcmp(curCmd->name, (const xmlChar *) "text"))
curCmd = curCmd->next;
curCmd = xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Object", (const xmlChar *)"");
xmlNewProp (curCmd, (const xmlChar *)"Application", (const xmlChar *)objSvc);
xmlNewProp (curCmd, (const xmlChar *)"Type", (const xmlChar *)objAppn);
//curCmd = xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Name", (const xmlChar *)objName);
xmlNewProp (curCmd, (const xmlChar *)"Name", (const xmlChar *)objName);
curRespWeb = xmlDocGetRootElement(docRespWeb);
xmlAddChild(curCmd, xmlCopyNodeList(curRespWeb));
}
void InsertResponseObjectError(const int id, const char *severity, const char *description, const char *externalDesc, xmlDocPtr **docCmd)
{
xmlNodePtr curCmd;
char dummyId[10]="";
/* Set Pointer */
curCmd = xmlDocGetRootElement(**docCmd);
curCmd = curCmd->xmlChildrenNode;
curCmd = xmlGetLastChild(curCmd);
/* Insert Error */
curCmd = xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Error", (const xmlChar *)"");
sprintf(dummyId, "%d", id);
xmlNewProp (curCmd, (const xmlChar *)"Id", (const xmlChar *)dummyId);
xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Severity", (const xmlChar *)severity);
xmlNewTextChild (curCmd, NULL, (const xmlChar *)"Description", (const xmlChar *)description);
xmlNewTextChild (curCmd, NULL, (const xmlChar *)"ExternalDescription", (const xmlChar *)externalDesc);
}
void SetResponseCommandStatus(const int cmdStatus, xmlDocPtr **docCmd)
{
xmlNodePtr curCmd;
/* Write Status */
curCmd = xmlDocGetRootElement(**docCmd);
curCmd = curCmd->xmlChildrenNode;
while (curCmd != NULL)
{
if (!xmlStrcmp(curCmd->name, (const xmlChar *) "Command"))
break;
curCmd = curCmd->next;
}
if (cmdStatus == 0)
xmlNewProp (curCmd, (const xmlChar *)"Status", (const xmlChar *)"Ok");
else if (cmdStatus == 1)
xmlNewProp (curCmd, (const xmlChar *)"Status", (const xmlChar *)"Warning");
else if (cmdStatus == 2)
xmlNewProp (curCmd, (const xmlChar *)"Status", (const xmlChar *)"Error");
}
void MergeResponse(const xmlDocPtr docSrc, xmlDocPtr *docDest)
{
xmlNodePtr curSrc, curDest;
/* Set pointer in source document */
curDest = xmlDocGetRootElement(*docDest);
curDest = curDest->xmlChildrenNode;
while (curDest != NULL)
{
if (!xmlStrcmp(curDest->name, (const xmlChar *) "Web"))
break;
curDest = curDest->next;
}
/* Set pointer in destination document */
curSrc = xmlDocGetRootElement(docSrc);
curSrc = curSrc->xmlChildrenNode;
while (curSrc != NULL)
{
if (!xmlStrcmp(curSrc->name, (const xmlChar *) "Command"))
break;
curSrc = curSrc->next;
}
/* Merge */
xmlAddChild(curDest, xmlCopyNodeList(curSrc));
}
int CommandExec(const char *cmdName, const char *sessionId, const char *format, const xmlDocPtr docCmd, xmlDocPtr *docRespCmd)
{
xmlDocPtr docRespWeb;
xmlNodePtr curCmd, curPar, curPar2;
xmlChar *elementValue, *elementName;
char *objSvc, *objAppn, *objName, *externalError;
int cmdStatus = 0, retStatus = 0;
/* Create Command Response */
CreateResponseCommand(cmdName, sessionId, format, &docRespCmd);
/* Init node ptr */
curCmd = xmlDocGetRootElement(docCmd);
// buf = xmlBufferCreate();
// xmlNodeDump(buf, docCmd, curCmd, 0, 1);
// printf("\n%s\n", (char *)xmlBufferContent(buf));
// xmlBufferFree(buf);
/* Loop through all objects */
for (curCmd = curCmd->xmlChildrenNode; curCmd != NULL; curCmd = curCmd->next)
{
if (xmlStrcmp(curCmd->name, (const xmlChar *) "Object")) continue;
/* Get and store main parameters */
objSvc = (char *)xmlGetProp(curCmd, (const xmlChar *)"Service");
objAppn = (char *)xmlGetProp(curCmd, (const xmlChar *)"Application");
objName = (char *)xmlGetProp(curCmd, (const xmlChar *)"Name");
biWebPtr->putValue(&biWebPtr,"webcmd", cmdName);
biWebPtr->putValue(&biWebPtr,"service", objSvc);
biWebPtr->putValue(&biWebPtr,"appn", objAppn);
biWebPtr->putValue(&biWebPtr,"name", objName);
biWebPtr->putValue(&biWebPtr,"format", format);
/* Get and store additional parameters */
curPar = curCmd;
for (curPar = curPar->xmlChildrenNode; curPar != NULL; curPar = curPar->next)
{
if (xmlStrcmp(curPar->name, (const xmlChar *) "Parameters")) continue;
curPar2 = curPar;
for (curPar2 = curPar2->xmlChildrenNode; curPar2 != NULL; curPar2 = curPar2->next)
{
if (xmlStrcmp(curPar2->name, (const xmlChar *) "Parameter")) continue;
elementName = xmlGetProp(curPar2, (const xmlChar *)"Name");
elementValue = xmlNodeListGetString(docCmd, curPar2->xmlChildrenNode, 1);
biWebPtr->putValue(&biWebPtr,(const char *)elementName, (const char *)elementValue);
/* Clean up */
xmlFree(elementName);
xmlFree(elementValue);
}
}
/* Determine command and call appropriate function */
if (!strcmp(cmdName, "RunLogic"))
{
/* Insert Object */
/* Get Response */
retStatus = RunRunLogic(objSvc, objAppn, objName, format, &docRespWeb, &externalError);
if (retStatus == 0)
InsertResponseWeb(objSvc, objAppn, objName, docRespWeb, &docRespCmd);
else
InsertResponseObject(objSvc, objAppn, objName, &docRespCmd);
retStatus = 0;
}
else
{
/* Invalid Command */
InsertResponseObject(objSvc, objAppn, objName, &docRespCmd);
retStatus = 50007;
}
/* Error Handling */
if (retStatus != 0)
{
/* If external /3rd party error */
if (retStatus == 90001)
{
InsertResponseObjectError(retStatus, "Error", "External warning/error", externalError, &docRespCmd);
delete externalError;
cmdStatus = 2;
}
else
{
InsertResponseObjectError(retStatus, errorSeverity[errorTable50000[(retStatus-50000)].severity], errorTable50000[(retStatus-50000)].description, "", &docRespCmd);
if (cmdStatus < errorTable50000[(retStatus-50000)].severity)
cmdStatus = errorTable50000[(retStatus-50000)].severity;
}
}
}
/* Write Status */
SetResponseCommandStatus(cmdStatus, &docRespCmd);
/* Delete web parameter list */
biWebPtr->deleteList(&biWebPtr);
/* Return */
return 0;
}
xmlDocPtr RunCommand(const xmlDocPtr doc)
{
xmlDocPtr docResponse, docCmd, docRespCmd;
xmlNodePtr cur, curResponse;
char *cmdName, *sessionId, *format;
int retStatus;
/* Set up response document */
CreateResponse(&docResponse, &curResponse);
/* Init node ptr */
cur = xmlDocGetRootElement(doc);
/* Check if correct repository XML and version */
cur = cur->xmlChildrenNode;
if (!xmlStrcmp(cur->name, (const xmlChar *) "text"))
cur = cur->next;
/* Loop through all Web Commands */
for (cur = cur->xmlChildrenNode; cur != NULL; cur = cur->next)
{
if (xmlStrcmp(cur->name, (const xmlChar *) "Command")) continue;
/* Get command name */
cmdName = (char *)xmlGetProp(cur, (const xmlChar *)"Name");
/* Get session Id */
sessionId = (char *)xmlGetProp(cur, (const xmlChar *) "SessionId");
/* Get response format */
format = (char *)xmlGetProp(cur, (const xmlChar *) "Format");
/* Create Command document */
CreateCommandDoc(cur, &docCmd);
/* Execute Command */
retStatus = CommandExec(cmdName, sessionId, format, docCmd, &docRespCmd);
/* Merge response level2 in level1 */
MergeResponse(docRespCmd, &docResponse);
/* Release Command Doc */
xmlFreeDoc(docCmd);
xmlFreeDoc(docRespCmd);
}
/* Return */
return docResponse;
}