mirror of
https://github.com/oatpp/oatpp-postgresql.git
synced 2024-11-27 02:39:56 +08:00
ql_template::Parser: Introduce 'CleanSections'
This commit is contained in:
parent
72a1536050
commit
2b9f0d9455
@ -29,14 +29,15 @@
|
||||
|
||||
namespace oatpp { namespace postgresql { namespace ql_template {
|
||||
|
||||
oatpp::String Parser::preprocess(const oatpp::String& text) {
|
||||
oatpp::String Parser::preprocess(const oatpp::String& text, std::vector<CleanSection>& cleanSections) {
|
||||
|
||||
data::stream::BufferOutputStream ss;
|
||||
parser::Caret caret(text);
|
||||
|
||||
bool ignore = false;
|
||||
bool writeChar = true;
|
||||
|
||||
v_buff_size sectionStart = -1;
|
||||
|
||||
while(caret.canContinue()) {
|
||||
|
||||
v_char8 c = *caret.getCurrData();
|
||||
@ -58,26 +59,32 @@ oatpp::String Parser::preprocess(const oatpp::String& text) {
|
||||
writeChar = false;
|
||||
break;
|
||||
}
|
||||
|
||||
case '<': {
|
||||
caret.inc();
|
||||
if(!ignore) {
|
||||
ignore = caret.canContinue() && caret.isAtChar('[');
|
||||
if(ignore) {
|
||||
caret.inc();
|
||||
if(sectionStart == -1) {
|
||||
if(caret.isAtText((p_char8) "<!!", 3, true)) {
|
||||
sectionStart = ss.getCurrentPosition();
|
||||
writeChar = false;
|
||||
} else {
|
||||
caret.inc();
|
||||
}
|
||||
} else {
|
||||
caret.inc();
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case ']': {
|
||||
caret.inc();
|
||||
if(ignore) {
|
||||
ignore = !(caret.canContinue() && caret.isAtChar('>'));
|
||||
if(!ignore) {
|
||||
caret.inc();
|
||||
case '!': {
|
||||
if(sectionStart != -1) {
|
||||
if(caret.isAtText((p_char8) "!!>", 3, true)) {
|
||||
cleanSections.emplace_back(CleanSection(sectionStart, ss.getCurrentPosition() - sectionStart));
|
||||
sectionStart = -1;
|
||||
writeChar = false;
|
||||
} else {
|
||||
caret.inc();
|
||||
}
|
||||
} else {
|
||||
caret.inc();
|
||||
}
|
||||
break;
|
||||
}
|
||||
@ -88,11 +95,7 @@ oatpp::String Parser::preprocess(const oatpp::String& text) {
|
||||
}
|
||||
|
||||
if(writeChar) {
|
||||
if (ignore) {
|
||||
ss.writeCharSimple('_');
|
||||
} else {
|
||||
ss.writeCharSimple(c);
|
||||
}
|
||||
ss.writeCharSimple(c);
|
||||
}
|
||||
|
||||
}
|
||||
@ -172,11 +175,23 @@ void Parser::skipStringInDollars(parser::Caret& caret) {
|
||||
|
||||
data::share::StringTemplate Parser::parseTemplate(const oatpp::String& text) {
|
||||
|
||||
std::vector<CleanSection> cleanSections;
|
||||
auto processedText = preprocess(text, cleanSections);
|
||||
|
||||
parser::Caret caret(processedText);
|
||||
|
||||
std::vector<data::share::StringTemplate::Variable> variables;
|
||||
|
||||
parser::Caret caret(preprocess(text));
|
||||
v_buff_size currSection = 0;
|
||||
|
||||
while(caret.canContinue()) {
|
||||
|
||||
if(currSection < cleanSections.size() && cleanSections[currSection].position == caret.getPosition()) {
|
||||
caret.inc(cleanSections[currSection].size);
|
||||
currSection ++;
|
||||
continue;
|
||||
}
|
||||
|
||||
v_char8 c = *caret.getCurrData();
|
||||
|
||||
switch(c) {
|
||||
@ -203,7 +218,7 @@ data::share::StringTemplate Parser::parseTemplate(const oatpp::String& text) {
|
||||
throw oatpp::parser::ParsingError(caret.getErrorMessage(), caret.getErrorCode(), caret.getPosition());
|
||||
}
|
||||
|
||||
return data::share::StringTemplate(text, std::move(variables));
|
||||
return data::share::StringTemplate(processedText, std::move(variables));
|
||||
|
||||
}
|
||||
|
||||
|
@ -65,6 +65,16 @@ public:
|
||||
|
||||
};
|
||||
|
||||
public:
|
||||
|
||||
struct CleanSection {
|
||||
CleanSection(v_buff_size p, v_buff_size s)
|
||||
: position(p)
|
||||
, size(s)
|
||||
{}
|
||||
v_buff_size position;
|
||||
v_buff_size size;
|
||||
};
|
||||
|
||||
private:
|
||||
static data::share::StringTemplate::Variable parseIdentifier(parser::Caret& caret);
|
||||
@ -75,9 +85,10 @@ public:
|
||||
/**
|
||||
* Preprocess text.
|
||||
* @param text
|
||||
* @param cleanSections - out vector of clean sections.
|
||||
* @return
|
||||
*/
|
||||
static oatpp::String preprocess(const oatpp::String& text);
|
||||
static oatpp::String preprocess(const oatpp::String& text, std::vector<CleanSection>& cleanSections);
|
||||
|
||||
/**
|
||||
* Parse query template.
|
||||
|
@ -36,49 +36,227 @@ typedef oatpp::postgresql::ql_template::Parser Parser;
|
||||
|
||||
void ParserTest::onRun() {
|
||||
|
||||
// {
|
||||
// oatpp::String text = "";
|
||||
// auto result = Parser::preprocess(text);
|
||||
// OATPP_ASSERT(result == text);
|
||||
// }
|
||||
//
|
||||
// {
|
||||
// oatpp::String text = "SELECT * FROM my_table;";
|
||||
// auto result = Parser::preprocess(text);
|
||||
// OATPP_ASSERT(result == text);
|
||||
// }
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <[ * ]> FROM my_table;";
|
||||
auto result = Parser::preprocess(text);
|
||||
OATPP_ASSERT(result == "SELECT ___ FROM my_table;");
|
||||
oatpp::String text = "";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(result == text);
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "<[SELECT * FROM my_table;]>";
|
||||
auto result = Parser::preprocess(text);
|
||||
OATPP_ASSERT(result == "_______________________");
|
||||
oatpp::String text = "SELECT * FROM my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(result == text);
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <[ * ]> FROM]> my_table;";
|
||||
auto result = Parser::preprocess(text);
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->getData());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->getData());
|
||||
oatpp::String text = "SELECT <!! * !!> FROM my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 1);
|
||||
OATPP_ASSERT(result == "SELECT * FROM my_table;");
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 7);
|
||||
OATPP_ASSERT(s.size == 3);
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT < [ * ] > FROM]> my_table;";
|
||||
auto result = Parser::preprocess(text);
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->getData());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->getData());
|
||||
oatpp::String text = "<!!SELECT * FROM my_table;!!>";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 1);
|
||||
OATPP_ASSERT(result == "SELECT * FROM my_table;");
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 0);
|
||||
OATPP_ASSERT(s.size == result->getSize());
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <[ * ']>' FROM my_table;";
|
||||
auto result = Parser::preprocess(text);
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->getData());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->getData());
|
||||
oatpp::String text = "SELECT <!! * !!> FROM!!> my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 1);
|
||||
OATPP_ASSERT(result == "SELECT * FROM!!> my_table;");
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 7);
|
||||
OATPP_ASSERT(s.size == 3);
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <!! <!!* !!> FROM!!> my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 1);
|
||||
OATPP_ASSERT(result == "SELECT <!!* FROM!!> my_table;");
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 7);
|
||||
OATPP_ASSERT(s.size == 6);
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT < !! * !! > FROM!!> my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 0);
|
||||
OATPP_ASSERT(result == text);
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <!! schedule[1:2][2] !!> FROM <!!my_table!!>;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 2);
|
||||
OATPP_ASSERT(result == "SELECT schedule[1:2][2] FROM my_table;");
|
||||
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 7);
|
||||
OATPP_ASSERT(s.size == 18);
|
||||
}
|
||||
|
||||
{
|
||||
const auto& s = sections[1];
|
||||
OATPP_ASSERT(s.position == 31);
|
||||
OATPP_ASSERT(s.size == 8);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <!! * '!!>' FROM!!> my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 1);
|
||||
OATPP_ASSERT(result == "SELECT * '!!>' FROM my_table;");
|
||||
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 7);
|
||||
OATPP_ASSERT(s.size == 13);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT '<!!' * <!! FROM!!> my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 1);
|
||||
OATPP_ASSERT(result == "SELECT '<!!' * FROM my_table;");
|
||||
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 15);
|
||||
OATPP_ASSERT(s.size == 5);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT * <!!!!> FROM my_table;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto result = Parser::preprocess(text, sections);
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(sections.size() == 1);
|
||||
OATPP_ASSERT(result == "SELECT * FROM my_table;");
|
||||
|
||||
{
|
||||
const auto& s = sections[0];
|
||||
OATPP_ASSERT(s.position == 9);
|
||||
OATPP_ASSERT(s.size == 0);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <!! name::text !!> FROM my_table WHERE id=:id;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto temp = Parser::parseTemplate(text);
|
||||
auto result = temp.format("<val>");
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(result == "SELECT name::text FROM my_table WHERE id=<val>;");
|
||||
}
|
||||
|
||||
{
|
||||
oatpp::String text = "SELECT <!! name::text !!> FROM my_table WHERE <!! id=:id !!>;";
|
||||
std::vector<Parser::CleanSection> sections;
|
||||
auto temp = Parser::parseTemplate(text);
|
||||
auto result = temp.format("<val>");
|
||||
|
||||
OATPP_LOGD(TAG, "--- case ---");
|
||||
OATPP_LOGD(TAG, "sql='%s'", text->c_str());
|
||||
OATPP_LOGD(TAG, "res='%s'", result->c_str());
|
||||
|
||||
OATPP_ASSERT(result == "SELECT name::text FROM my_table WHERE id=:id ;");
|
||||
}
|
||||
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user