Skip to content

Instantly share code, notes, and snippets.

@ql-owo-lp
Created March 20, 2013 00:48
Show Gist options
  • Save ql-owo-lp/5201476 to your computer and use it in GitHub Desktop.
Save ql-owo-lp/5201476 to your computer and use it in GitHub Desktop.
CIS 687 XmlTranslator for Project 1 & 2
#ifndef XMLENCODER_H
#define XMLENCODER_H
#include <string>
// the translator class of XmlReader / XmlWriter
class XmlEncoder {
// escape markup
static std::string encodeAttr(std::string str) {
std::string buffer;
buffer.reserve(str.length());
for(size_t pos = 0; pos < str.length(); pos++) {
switch(str[pos]) { // escape the five XML built-in markups
case '&': buffer.append("&amp;"); break;
case '\"': buffer.append("&quot;"); break;
case '\'': buffer.append("&apos;"); break;
case '<': buffer.append("&lt;"); break;
case '>': buffer.append("&gt;"); break;
default: buffer.append(1,str[pos]); break;
}
}
return buffer.c_str();
}
// unescape markup
static std::string decodeAttr(std::string str) {
std::string buffer;
buffer.reserve(str.length());
for(size_t pos = 0, specialTokLength=0; pos < str.length(); pos++) {
buffer.append(1, str[pos]); // append first
if (str[pos]=='&')
specialTokLength=1; // always count from the latest ampersand
else if (specialTokLength>0 && str[pos]==';') {
size_t specialTokPos = pos - (specialTokLength++);
std::string specialTok = str.substr(specialTokPos, specialTokLength);
char chr='\0'; // empty char by default
if (specialTok=="&amp;") chr='&';
else if (specialTok=="&quot;") chr='"';
else if (specialTok=="&apos;") chr='\'';
else if (specialTok=="&lt;") chr='<';
else if (specialTok=="&gt;") chr='>';
if (chr!='\0')
buffer.replace(buffer.length()-specialTokLength, specialTokLength, 1, chr);
specialTokLength=0; // reset
}
}
return buffer.c_str();
}
// encode text is pretty simple, a lazy way is just to add the CDATA
// not used by current project, but I am gonna implement it anyway
static std::string encodeText(std::string str) {
std::string buffer("<![CDATA[");
buffer.reserve(str.length());
for (size_t pos=0; pos<str.length();pos++) {
buffer.append(1,str[pos]);
if (str[pos]=='>' && buffer.substr(buffer.length()-3)=="]]>")
buffer.replace(buffer.length()-3,3,"]]><![CDATA[]]]]><![CDATA[>"); // a tricky way to replace ]]>
}
buffer.append("]]>");
return buffer.c_str();
}
// decode test, simply by deleting all <!CDATA[ and ]]> markup
static std::string decodeText(std::string str) {
std::string buffer;
buffer.reserve(str.length());
for (size_t pos=0; pos<str.length();pos++) {
buffer.append(1,str[pos]);
if (str[pos]=='[' && buffer.substr(buffer.length()-9)=="<![CDATA[")
buffer.erase(buffer.length()-9);
else if (str[pos]=='>' && buffer.substr(buffer.length()-3)=="]]>")
buffer.erase(buffer.length()-3);
}
return buffer.c_str();
}
};
#endif
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment