📄 httpform.cxx
字号:
while (FindSpliceField(ValueRegEx, "", text, pos+len, fields, pos, len, start, finish, field)) {
if (field != NULL)
text.Splice(field->GetValue(), pos, len);
}
pos = len = 0;
static PRegularExpression InputRegEx("<input[ \t\r\n][^>]*name[ \t\r\n]*=[ \t\r\n]*\"[^\"]*\"[^>]*>",
PRegularExpression::Extended|PRegularExpression::IgnoreCase);
while (FindSpliceField(InputRegEx, "", text, pos+len, fields, pos, len, start, finish, field)) {
if (field != NULL) {
static PRegularExpression HiddenRegEx("type[ \t\r\n]*=[ \t\r\n]*\"?hidden\"?",
PRegularExpression::Extended|PRegularExpression::IgnoreCase);
PString substr = text.Mid(pos, len);
if (substr.FindRegEx(HiddenRegEx) == P_MAX_INDEX)
text.Splice(field->GetHTMLInput(substr), pos, len);
}
}
pos = len = 0;
static PRegularExpression SelectRegEx("<select[ \t\r\n][^>]*name[ \t\r\n]*=[ \t\r\n]*\"[^\"]*\"[^>]*>",
PRegularExpression::Extended|PRegularExpression::IgnoreCase);
static PRegularExpression SelEndRegEx("</select[^>]*>",
PRegularExpression::Extended|PRegularExpression::IgnoreCase);
while (FindSpliceField(SelectRegEx, SelEndRegEx, text, pos+len, fields, pos, len, start, finish, field)) {
if (field != NULL)
text.Splice(field->GetHTMLSelect(text(start, finish)), start, finish-start+1);
}
pos = len = 0;
static PRegularExpression TextRegEx("<textarea[ \t\r\n][^>]*name[ \t\r\n]*=[ \t\r\n]*\"[^\"]*\"[^>]*>",
PRegularExpression::Extended|PRegularExpression::IgnoreCase);
static PRegularExpression TextEndRegEx("</textarea[^>]*>", PRegularExpression::IgnoreCase);
while (FindSpliceField(TextRegEx, TextEndRegEx, text, pos+len, fields, pos, len, start, finish, field)) {
if (field != NULL)
text.Splice(field->GetValue(), start, finish-start+1);
}
}
PHTTPField * PHTTPForm::Add(PHTTPField * fld)
{
PAssertNULL(fld);
PAssert(!fieldNames[fld->GetName()], "Field already on form!");
fieldNames += fld->GetName();
fields.Append(fld);
return fld;
}
void PHTTPForm::BuildHTML(const char * heading)
{
PHTML html(heading);
BuildHTML(html);
}
void PHTTPForm::BuildHTML(const PString & heading)
{
PHTML html(heading);
BuildHTML(html);
}
void PHTTPForm::BuildHTML(PHTML & html, BuildOptions option)
{
if (!html.Is(PHTML::InForm))
html << PHTML::Form("POST");
html << PHTML::TableStart();
for (PINDEX fld = 0; fld < fields.GetSize(); fld++) {
PHTTPField & field = fields[fld];
if (field.NotYetInHTML()) {
html << PHTML::TableRow()
<< PHTML::TableData("align=right")
<< field.GetTitle()
<< PHTML::TableData("align=left")
<< "<!--#form html " << field.GetName() << "-->"
<< PHTML::TableData()
<< field.GetHelp();
field.SetInHTML();
}
}
html << PHTML::TableEnd();
if (option != InsertIntoForm)
html << PHTML::Paragraph()
<< ' ' << PHTML::SubmitButton("Accept")
<< ' ' << PHTML::ResetButton("Reset")
<< PHTML::Form();
if (option == CompleteHTML) {
html << PHTML::Body();
string = html;
}
}
BOOL PHTTPForm::Post(PHTTPRequest & request,
const PStringToString & data,
PHTML & msg)
{
PString prefix = request.url.GetQueryVars()("subformprefix");
const PHTTPField * field = NULL;
if (!prefix)
field = fields.LocateName(prefix);
if (field == NULL)
field = &fields;
PStringStream errors;
if (field->ValidateAll(data, errors)) {
((PHTTPField *)field)->SetAllValues(data);
if (msg.IsEmpty())
msg = "Accepted New Configuration";
else {
PString block;
PINDEX pos = 0;
PINDEX len, start, finish;
while (FindSpliceAccepted(msg, pos, pos, len, start, finish))
msg.Splice(msg(start, finish), pos, len);
pos = 0;
while (FindSpliceErrors(msg, pos, pos, len, start, finish))
msg.Delete(pos, len);
}
}
else {
request.code = PHTTP::BadRequest;
if (msg.IsEmpty()) {
msg = "Validation Error in Request";
msg << errors;
}
else {
PINDEX pos = 0;
PINDEX len, start, finish;
while (FindSpliceAccepted(msg, pos, pos, len, start, finish))
msg.Delete(pos, len);
BOOL appendErrors = TRUE;
pos = 0;
while (FindSpliceErrors(msg, pos, pos, len, start, finish)) {
PString block = msg(start, finish);
PINDEX vPos, vLen;
static PRegularExpression Validation("<?!--#form[ \t\r\n]+validation[ \t\r\n]*-->?",
PRegularExpression::Extended|PRegularExpression::IgnoreCase);
if (block.FindRegEx(Validation, vPos, vLen))
block.Splice(errors, vPos, vLen);
else
block += errors;
msg.Splice(block, pos, len);
appendErrors = FALSE;
}
if (appendErrors)
msg << errors;
}
}
return TRUE;
}
//////////////////////////////////////////////////////////////////////////////
// PHTTPConfig
PHTTPConfig::PHTTPConfig(const PURL & url,
const PString & sect)
: PHTTPForm(url), section(sect)
{
Construct();
}
PHTTPConfig::PHTTPConfig(const PURL & url,
const PString & sect,
const PHTTPAuthority & auth)
: PHTTPForm(url, auth), section(sect)
{
Construct();
}
PHTTPConfig::PHTTPConfig(const PURL & url,
const PString & html,
const PString & sect)
: PHTTPForm(url, html), section(sect)
{
Construct();
}
PHTTPConfig::PHTTPConfig(const PURL & url,
const PString & html,
const PString & sect,
const PHTTPAuthority & auth)
: PHTTPForm(url, html, auth), section(sect)
{
Construct();
}
void PHTTPConfig::Construct()
{
sectionField = NULL;
keyField = NULL;
valField = NULL;
}
void PHTTPConfig::LoadFromConfig()
{
PConfig cfg(section);
fields.LoadFromConfig(cfg);
}
void PHTTPConfig::OnLoadedText(PHTTPRequest & request, PString & text)
{
if (sectionField == NULL) {
PString sectionName = request.url.GetQueryVars()("section", section);
if (!sectionName) {
section = sectionName;
LoadFromConfig();
}
}
PHTTPForm::OnLoadedText(request, text);
}
BOOL PHTTPConfig::Post(PHTTPRequest & request,
const PStringToString & data,
PHTML & msg)
{
// Make sure the internal structure is up to date before accepting new data
if (!section)
LoadFromConfig();
PSortedStringList oldValues;
// Remember fields that are here now, so can delete removed array fields
PINDEX fld;
for (fld = 0; fld < fields.GetSize(); fld++) {
PHTTPField & field = fields[fld];
if (&field != keyField && &field != valField && &field != sectionField) {
PStringList names = field.GetAllNames();
for (PINDEX i = 0; i < names.GetSize(); i++)
oldValues.AppendString(names[i]);
}
}
PHTTPForm::Post(request, data, msg);
if (request.code != PHTTP::OK)
return TRUE;
if (sectionField != NULL)
section = sectionPrefix + sectionField->GetValue() + sectionSuffix;
PString sectionName = request.url.GetQueryVars()("section", section);
if (sectionName.IsEmpty())
return TRUE;
PConfig cfg(sectionName);
for (fld = 0; fld < fields.GetSize(); fld++) {
PHTTPField & field = fields[fld];
if (&field == keyField) {
PString key = field.GetValue();
if (!key)
cfg.SetString(key, valField->GetValue());
}
else if (&field != valField && &field != sectionField)
field.SaveToConfig(cfg);
}
// Find out which fields have been removed (arrays elements deleted)
for (fld = 0; fld < fields.GetSize(); fld++) {
PHTTPField & field = fields[fld];
if (&field != keyField && &field != valField && &field != sectionField) {
PStringList names = field.GetAllNames();
for (PINDEX i = 0; i < names.GetSize(); i++) {
PINDEX idx = oldValues.GetStringsIndex(names[i]);
if (idx != P_MAX_INDEX)
oldValues.RemoveAt(idx);
}
}
}
for (fld = 0; fld < oldValues.GetSize(); fld++) {
PString section, key;
switch (SplitConfigKey(oldValues[fld], section, key)) {
case 1 :
cfg.DeleteKey(key);
break;
case 2 :
cfg.DeleteKey(section, key);
if (cfg.GetKeys(section).IsEmpty())
cfg.DeleteSection(section);
}
}
section = sectionName;
return TRUE;
}
PHTTPField * PHTTPConfig::AddSectionField(PHTTPField * sectionFld,
const char * prefix,
const char * suffix)
{
sectionField = PAssertNULL(sectionFld);
PAssert(!sectionField->IsDescendant(PHTTPCompositeField::Class()), "Section field is composite");
Add(sectionField);
if (prefix != NULL)
sectionPrefix = prefix;
if (suffix != NULL)
sectionSuffix = suffix;
return sectionField;
}
void PHTTPConfig::AddNewKeyFields(PHTTPField * keyFld,
PHTTPField * valFld)
{
keyField = PAssertNULL(keyFld);
Add(keyFld);
valField = PAssertNULL(valFld);
Add(valFld);
}
//////////////////////////////////////////////////////////////////////////////
// PHTTPConfigSectionList
static const char FormListInclude[] = "<!--#form pagelist-->";
PHTTPConfigSectionList::PHTTPConfigSectionList(const PURL & url,
const PHTTPAuthority & auth,
const PString & prefix,
const PString & valueName,
const PURL & editSection,
const PURL & newSection,
const PString & newTitle,
PHTML & heading)
: PHTTPString(url, auth),
sectionPrefix(prefix),
additionalValueName(valueName),
newSectionLink(newSection.AsString(PURL::URIOnly)),
newSectionTitle(newTitle),
editSectionLink(editSection.AsString(PURL::URIOnly) +
"?section=" + PURL::TranslateString(prefix, PURL::QueryTranslation))
{
if (heading.Is(PHTML::InBody))
heading << FormListInclude << PHTML::Body();
SetString(heading);
}
void PHTTPConfigSectionList::OnLoadedText(PHTTPRequest &, PString & text)
{
PConfig cfg;
PStringList nameList = cfg.GetSections();
PINDEX pos = text.Find(FormListInclude);
if (pos != P_MAX_INDEX) {
PINDEX endpos = text.Find(FormListInclude, pos + sizeof(FormListInclude)-1);
if (endpos == P_MAX_INDEX) {
PHTML html(PHTML::InBody);
html << PHTML::Form("POST") << PHTML::TableStart();
PINDEX i;
for (i = 0; i < nameList.GetSize(); i++) {
if (nameList[i].Find(sectionPrefix) == 0) {
PString name = nameList[i].Mid(sectionPrefix.GetLength());
html << PHTML::TableRow()
<< PHTML::TableData()
<< PHTML::HotLink(editSectionLink + PURL::TranslateString(name, PURL::QueryTranslation))
<< name
<< PHTML::HotLink();
if (!additionalValueName)
html << PHTML::TableData()
<< PHTML::HotLink(editSectionLink + PURL::TranslateString(name, PURL::QueryTranslation))
<< cfg.GetString(nameList[i], additionalValueName, "")
<< PHTML::HotLink();
html << PHTML::TableData() << PHTML::SubmitButton("Remove", name);
}
}
html << PHTML::TableRow()
<< PHTML::TableData()
<< PHTML::HotLink(newSectionLink)
<< newSectionTitle
<< PHTML::HotLink()
<< PHTML::TableEnd()
<< PHTML::Form();
text.Splice(html, pos, sizeof(FormListInclude)-1);
}
else {
PString repeat = text(pos + sizeof(FormListInclude)-1, endpos-1);
text.Delete(pos, endpos - pos);
PINDEX i;
for (i = 0; i < nameList.GetSize(); i++) {
if (nameList[i].Find(sectionPrefix) == 0) {
PString name = nameList[i].Mid(sectionPrefix.GetLength());
text.Splice(repeat, pos, 0);
text.Replace("<!--#form hotlink-->",
editSectionLink + PURL::TranslateString(name, PURL::QueryTranslation),
TRUE, pos);
if (!additionalValueName)
text.Replace("<!--#form additional-->",
cfg.GetString(nameList[i], additionalValueName, ""),
TRUE, pos);
text.Replace("<!--#form section-->", name, TRUE, pos);
pos = text.Find(FormListInclude, pos);
}
}
text.Delete(text.Find(FormListInclude, pos), sizeof(FormListInclude)-1);
}
}
}
BOOL PHTTPConfigSectionList::Post(PHTTPRequest &,
const PStringToString & data,
PHTML & replyMessage)
{
PConfig cfg;
PStringList nameList = cfg.GetSections();
PINDEX i;
for (i = 0; i < nameList.GetSize(); i++) {
if (nameList[i].Find(sectionPrefix) == 0) {
PString name = nameList[i].Mid(sectionPrefix.GetLength());
if (data.Contains(name)) {
cfg.DeleteSection(nameList[i]);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -