campo-sirio/server/postman.cpp
luca d0a2f8e2ec Patch level :10.0
Files correlati     :
Ricompilazione Demo : [ ]
Commento            :corretti warning


git-svn-id: svn://10.65.10.50/trunk@16571 c028cbd2-c16b-5b4b-a496-9718f37d4682
2008-05-06 09:26:00 +00:00

639 lines
14 KiB
C++
Executable File

#include "baseserv.h"
#include "xml.h"
#include <wx/config.h>
#include <wx/filename.h>
#include <wx/tokenzr.h>
#ifdef WIN32
#include <wx/fileconf.h>
#endif
#define LF_TABGEN 3
#define LF_TABCOM 4
#define LF_TAB 5
//////////////////////////////////////////////////////////
// Date utilities
///////////////////////////////////////////////////////////
static const byte _days_in_month[12] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
int last_day(int month, int year)
// parse_filastrok(
// "trenta giorni ha novembre
// con april, giugno e settembre
// son ventotto case uno
// per default ce n'ha trentuno");
{
int d = _days_in_month[month-1];
if (month == 2 && (year % 4) == 0)
d++;
return d;
}
bool isdate(const wxChar * s)
{
const int len = strlen(s);
if (len != 8 && len != 10)
return false;
int d = 0, m = 0, y = 0, i;
if (len == 8)
{
for (i = 0; i < 8; i++)
if (!isdigit(s[i])) break;
if (i == 8)
{
wxString str(s);
d = atoi(((const char *)str)+6); str[6] = '\0';
m = atoi(((const char *)str)+4); str[4] = '\0';
y = atoi(((const char *)str)+0);
}
}
else
if (len == 10)
{
if (s[2] == s[5] && !isdigit(s[2]))
{
d = atoi(s);
m = atoi(&s[3]);
y = atoi(&s[6]);
}
}
if (d < 1 || d > 31 ||
m < 1 || m > 12 ||
y < 0)
return false;
return d <= last_day(m,y);
}
long date2ansi(const wxChar * s)
{
long val = 0L;
const int len = (s && *s >= '0') ? strlen(s) : 0;
if (len != 8 && len != 10) // Chi si azzarda ad aggiungere len != 6 ?
return 0L;
if (len == 8)
{
int i;
for (i = 0; i < 8; i++)
if (!isdigit(s[i])) break;
if (i == 8)
val = atol(s);
}
else
{
if (s[2] == s[5] && !isdigit(s[2]))
{
const int d = atoi(s);
const int m = atoi(&s[3]);
const int y = atoi(&s[6]);
val = d + m + 100 + y * 10000;
}
}
return val;
}
///////////////////////////////////////////////////////////
// TPostmanServer
///////////////////////////////////////////////////////////
class TPostmanServer : public TBaseServerApp
{
wxArrayString m_Editors;
wxArrayString m_FirmEditors;
int m_Logicnum;
int m_Firm;
int m_LastFirm;
wxArrayString m_TableName;
int m_Err;
wxString m_DataPath;
protected:
virtual void ProcessHttpGet(wxString cmd, wxSocketBase& outs);
bool IsMagicName(wxString& strFilename) const;
virtual const wxChar* GetAppName() const;
void AbsoluteNameName(wxString & name);
const wxString Table2Editor(const wxString & table);
bool LoadEditors(const wxChar * filename, wxArrayString & editors);
void SaveXml2IniParagraph(wxFileConfig & ini, TXmlItem& xmlItem);
void SaveTransaction(const TXmlItem& xmlMethod, wxString & filename);
void AdjustTransaction(wxString & filename);
const wxString EditorCommand();
void ExecuteTransaction(wxString & filename);
void LoadXmlParagraph(TXmlItem & xmlItem, wxString & paragraph, wxString & filename);
void LoadTransaction(wxString & filename, TXmlItem & xmlAnswer);
void Log(TXmlItem& xmlItem, wxString & filename);
virtual void SoapProcessMethod(const TXmlItem& xmlMethod, TXmlItem& xmlAnswer);
virtual int GetDefaultPort() const;
public:
virtual bool Initialization();
TPostmanServer() : m_Logicnum(0), m_Err(0), m_Firm(0), m_LastFirm(0) {}
};
void TPostmanServer::ProcessHttpGet(wxString cmd, wxSocketBase& outs)
{
const int stop = cmd.Find(" HTTP");
wxString str = cmd.Mid(4, stop-4).Trim();
if (str == "/")
str += "index.htm";
wxString strFilename = GetDocumentRoot() + str;
IsMagicName(strFilename);
SendFile(strFilename, outs);
}
bool TPostmanServer::IsMagicName(wxString& strFilename) const
{
wxFileName fnName(strFilename);
wxString strName(fnName.GetName().Lower());
if (strName == "index" || strName == "log")
{
strFilename = GetLogFileName();
return true;
}
return false;
}
const wxString TPostmanServer::Table2Editor(const wxString & table)
{
wxString row;
wxString module;
wxString editor;
wxString name;
{
name << "../recdesc/d" << table << ".des";
name.Lower();
wxFileName f(name);
f.MakeAbsolute();
name = f.GetFullPath();
wxTextFile file(name);
if (file.Open())
{
for (row = file.GetFirstLine(); !file.Eof(); row = file.GetNextLine())
{
row.Trim(false);
if (row.StartsWith("Module"))
{
const int pos = row.Find("=");
if (pos >= 0)
module = row.Mid(pos + 1);
module.Trim();
module.Trim(false);
break;
}
}
}
}
if (module.IsEmpty())
{
module = "ba";
name = "../??tb";
name << table << ".msk";
name.Lower();
wxFileName f(name);
f.MakeAbsolute();
name = f.GetFullPath();
wxString foundfile = ::wxFindFirstFile(name, wxFILE);
while (!foundfile.IsEmpty())
{
f = foundfile;
wxString str(f.GetName().Left(2));
if (str != "ba")
{
module = str;
break;
}
foundfile = ::wxFindNextFile();
}
}
wxFileName f("../install.ini");
f.MakeAbsolute();
name = f.GetFullPath();
wxTextFile file(name);
wxString wmodule;
if (file.Open())
{
for (row = file.GetFirstLine(); !file.Eof(); row = file.GetNextLine())
{
row.Trim(false);
if (row.StartsWith("["))
wmodule = row.Mid(1, 2);
else
if (row.StartsWith("Edit_"))
{
const int pos = row.Find("=");
if (pos >= 0)
{
const wxString table(row.Mid(5, pos - 4));
const int logicnum = atoi(table);
if ((logicnum <= LF_TAB && module == wmodule) || table == m_TableName[m_Logicnum])
{
editor = row.Mid(pos + 1);
editor.Trim(false);
editor << " ";
if (m_Logicnum == LF_TABGEN)
editor << '#';
else
if (m_Logicnum == LF_TABCOM)
editor << '%';
editor << m_TableName[m_Logicnum];
if (table == m_TableName[m_Logicnum])
break;
}
}
}
}
}
return editor;
}
bool TPostmanServer::LoadEditors(const wxChar * filename, wxArrayString & editors)
{
wxFileName f(filename);
f.MakeAbsolute();
wxString name(f.GetFullPath());
wxTextFile file(name);
wxString row;
wxString module;
if (file.Open())
{
for (row = file.GetFirstLine(); !file.Eof(); row = file.GetNextLine())
{
wxString editor;
row.Trim(false);
if (row.StartsWith("["))
module = row.Mid(1, 2);
else
if (row.StartsWith("Edit_"))
{
const int pos = row.Find("=");
if (pos < 0)
continue;
const int logicnum = atoi(row.Mid(5, pos - 4));
if (logicnum < 7 && module != "ba")
continue;
editor = row.Mid(pos + 1);
editor.Trim(false);
int nrows2add = logicnum - editors.GetCount() + 1;
if (nrows2add > 0)
editors.Add(wxEmptyString, nrows2add);
editors[logicnum] = editor;
}
}
}
return editors.GetCount() > 0;
}
int TPostmanServer::GetDefaultPort() const
{
return GetConfigInt("Port", 8080);
}
void TPostmanServer::SaveXml2IniParagraph(wxFileConfig& ini, TXmlItem& xmlItem)
{
int items = xmlItem.GetChildren();
for (int i = 0; i < items; i++)
{
TXmlItem * child = xmlItem.GetChild(i);
wxString key(child->GetAttr("Name"));
wxString val(child->GetEnclosedText());
if (key == "Firm")
m_Firm = atoi(val);
ini.Write(key, val);
}
}
void TPostmanServer::SaveTransaction(const TXmlItem& xmlMethod, wxString & filename)
{
wxString paragraph;
int items = xmlMethod.GetChildren();
if (wxFileName::FileExists(filename))
wxRemoveFile(filename);
for (int i = 0; i < items; i++)
{
TXmlItem * child = xmlMethod.GetChild(i);
const int logicnum = atoi(child->GetAttr("LogicNumber"));
paragraph = "/";
if (logicnum > 0)
{
if (m_Logicnum == 0)
m_Logicnum = logicnum;
paragraph << logicnum;
const int rownum = atoi(child->GetAttr("RowNumber"));
if (rownum > 0)
paragraph << ',' << rownum;
int nrows2add = logicnum - m_TableName.GetCount() + 1;
if (nrows2add > 0)
m_TableName.Add(wxEmptyString, nrows2add);
m_TableName[logicnum] = child->GetAttr("TableName");
}
else
paragraph << child->GetTag();
wxFileConfig ini("", "", filename, "", wxCONFIG_USE_LOCAL_FILE | wxCONFIG_USE_RELATIVE_PATH);
ini.SetPath(paragraph);
SaveXml2IniParagraph(ini, *child);
}
}
void TPostmanServer::AdjustTransaction(wxString & filename)
{
wxTextFile file(filename);
bool changed = false;
if (file.Open())
{
for (wxString & row = file.GetFirstLine(); !file.Eof(); row = file.GetNextLine())
{
const int pos = row.Find("\\,");
if (pos > 0)
{
row.Remove(pos, 1);
changed = true;
size_t rowno = file.GetCurrentLine();
file.InsertLine(row, rowno);
file.RemoveLine(rowno + 1);
}
}
if (changed)
file.Write();
}
else
WriteLog("Can't create Transaction file");
}
const wxString TPostmanServer::EditorCommand()
{
const bool firmchanged = m_Firm != m_LastFirm;
m_LastFirm = m_Firm;
if (firmchanged)
{
m_FirmEditors.empty();
wxString name(m_DataPath);
wxChar l = name[name.Len() - 1];
if (l != '/' && l != '\\')
name << '/';
wxString str;
str << m_Firm;
while(str.Len() < 5)
str.insert(0, "0");
name << str << "a/ditta.ini";
LoadEditors(name.c_str(), m_FirmEditors);
}
wxString table(m_TableName[m_Logicnum]);
if (m_Logicnum <= LF_TAB && !table.IsEmpty())
{
wxString editor(Table2Editor(table));
if (!editor.IsEmpty())
return editor;
}
if (m_Logicnum < (int) m_FirmEditors.GetCount() && !m_FirmEditors[m_Logicnum].IsEmpty())
return m_FirmEditors[m_Logicnum].c_str();
if (m_Logicnum < (int) m_Editors.GetCount() && !m_Editors[m_Logicnum].IsEmpty())
return m_Editors[m_Logicnum].c_str();
return wxEmptyString;
}
void TPostmanServer::ExecuteTransaction(wxString & filename)
{
wxString editor(EditorCommand());
if (!editor.IsEmpty())
{
wxFileName cmdname(editor);
if (cmdname.IsRelative())
{
cmdname.MakeAbsolute();
cmdname.RemoveLastDir();
}
wxString command(cmdname.GetFullPath());
const wxString currdir(wxGetCwd());
wxSetWorkingDirectory(cmdname.GetPath());
command << " -i" <<filename << " -uADMIN";
m_Err = 0;
if (::wxExecute(command, wxEXEC_SYNC) < 0)
{
wxString str;
m_Err = 2;
str << "Errore nell'esecuzione di " << command << m_Err ;
WriteLog(str);
}
wxSetWorkingDirectory(currdir);
}
}
void TPostmanServer::LoadXmlParagraph(TXmlItem& xmlItem, wxString& paragraph, wxString & filename)
{
wxString path;
wxFileConfig ini("", "", filename, "", wxCONFIG_USE_LOCAL_FILE | wxCONFIG_USE_RELATIVE_PATH);
path << "/" << paragraph;
ini.SetPath(path);
wxStringTokenizer tok(paragraph, ",");
wxString tag = tok.GetNextToken();
const size_t logicnum = atoi(tag);
const wxChar * attr = logicnum > 0 ? "Field" : "Attr";
int rownum = 0 ;
if (logicnum > 0 && tok.HasMoreTokens())
rownum = atoi(tok.GetNextToken());
if (logicnum > 0)
tag = "Record";
TXmlItem & child =xmlItem.AddChild(tag);
if (logicnum > 0)
{
child.SetAttr("LogicNumber", logicnum);
if (logicnum < m_TableName.GetCount())
child.SetAttr("TableName", m_TableName[logicnum]);
if (rownum > 0)
child.SetAttr("RowNumber", rownum);
}
wxString s;
wxString key;
long index = 0;
for (bool ok = ini.GetFirstEntry(key, index); ok; ok = ini.GetNextEntry (key, index))
{
wxString val(ini.Read(key));
if (val.StartsWith("\"") && val.EndsWith("\""))
{
val = val.Mid(1);
val[val.Len()] = '\0';
}
else
{
val.Trim();
val.Trim(false);
}
if (isdate(val))
child.AddSoapInt(attr, date2ansi(val)).SetAttr("Name", key);
else
{
if (val.IsNumber())
{
if (key == "Error" && m_Err != 0)
child.AddSoapInt(attr, m_Err).SetAttr("Name", key);
else
child.AddSoapInt(attr, atoi(val)).SetAttr("Name", key);
}
else
{
if (key == "Result" && m_Err != 0)
child.AddSoapString(attr, "ERROR").SetAttr("Name", key);
else
child.AddSoapString(attr, val).SetAttr("Name", key);
}
}
}
}
void TPostmanServer::LoadTransaction(wxString & filename, TXmlItem& xmlAnswer)
{
wxString paragraph;
long index = 0;
wxFileConfig ini("", "", filename, "", wxCONFIG_USE_LOCAL_FILE | wxCONFIG_USE_RELATIVE_PATH);
for (bool ok = ini.GetFirstGroup(paragraph, index); ok; ok = ini.GetNextGroup(paragraph, index))
LoadXmlParagraph(xmlAnswer, paragraph, filename);
}
void TPostmanServer::Log(TXmlItem& WXUNUSED(xmlItem), wxString & filename)
{
wxFileConfig ini("", "", filename, "", wxCONFIG_USE_LOCAL_FILE | wxCONFIG_USE_RELATIVE_PATH);
wxString str;
wxString key;
long index = 0;
ini.SetPath("/Transaction");
str << "Transaction : Command " << m_Editors[m_Logicnum];
WriteLog(str);
for (bool ok = ini.GetFirstEntry(key, index); ok; ok = ini.GetNextEntry (key, index))
{
wxString val(ini.Read(key));
str = " ",
str << key << " = " << val;
WriteLog(str);
}
}
void TPostmanServer::SoapProcessMethod(const TXmlItem& xmlMethod, TXmlItem& xmlAnswer)
{
const wxString& strMethod = xmlMethod.GetTag();
if (strMethod == "m:CampoTransaction")
{
m_Logicnum = 0;
wxFileName filename(GetTempFilename("ini"));
wxString name(filename.GetFullPath());
SaveTransaction(xmlMethod, name);
AdjustTransaction(name);
ExecuteTransaction(name);
LoadTransaction(name, xmlAnswer);
Log(xmlAnswer, name);
}
}
// Implementazione delle due funzioni pure virtuali
const wxChar* TPostmanServer::GetAppName() const
{
return "Postman";
}
bool TPostmanServer::Initialization()
{
wxFileName f("../campo.ini");
f.MakeAbsolute();
wxString name(f.GetFullPath());
wxTextFile file(name);
wxString row;
if (file.Open())
{
for (row = file.GetFirstLine(); !file.Eof(); row = file.GetNextLine())
{
if (row.StartsWith("Study"))
{
const int pos = row.Find('=');
if (pos >= 0)
{
m_DataPath = row.Mid(pos + 1);
m_DataPath.Trim(false);
}
break;
}
}
}
if (m_DataPath.IsEmpty())
{
WriteLog("No data path");
return false;
}
if (!LoadEditors("../install.ini", m_Editors))
{
WriteLog("No editors found");
return false;
}
return true;
}
// Istanziare l'applicazione principale
IMPLEMENT_APP(TPostmanServer)