streamlet-examples/xpath.cpp
branchv_0
changeset 75 ecbf6504915c
parent 74 a2aa84f310a5
child 77 a680bcd946cd
equal deleted inserted replaced
74:a2aa84f310a5 75:ecbf6504915c
    51 		std::cmatch match;
    51 		std::cmatch match;
    52 		for (char **env = environ; *env; env++) if (std::regex_match(*env, match, xmlnsEnvPattern)) ns[std::string(match[1])] = match[2];
    52 		for (char **env = environ; *env; env++) if (std::regex_match(*env, match, xmlnsEnvPattern)) ns[std::string(match[1])] = match[2];
    53 	}
    53 	}
    54 
    54 
    55 	void findXmlnsInOptions() {
    55 	void findXmlnsInOptions() {
    56 		for (Option o : getOptions(std::wregex(L"xmlns[:_](.*)"))) ns[convertor.to_bytes(o.nameMatch[1])] = convertor.to_bytes(o.value);
    56 		for (Option o : getOptions(std::wregex(L"xmlns[:_](.*)"))) ns[toBytes(o.nameMatch[1])] = toBytes(o.value);
    57 		for (Option o : getOptions(std::wregex(L"xmlns"), std::wregex(L"([^:]+):(.*)"))) ns[convertor.to_bytes(o.valueMatch[1])] = convertor.to_bytes(o.valueMatch[2]);
    57 		for (Option o : getOptions(std::wregex(L"xmlns"), std::wregex(L"([^:]+):(.*)"))) ns[toBytes(o.valueMatch[1])] = toBytes(o.valueMatch[2]);
    58 	}
    58 	}
    59 
    59 
    60 	// Modes should share the logic of relpipe-in-xmltable
    60 	// Modes should share the logic of relpipe-in-xmltable
    61 
    61 
    62 	enum class Mode {
    62 	enum class Mode {
    72 		if (modeName == L"string") return Mode::STRING;
    72 		if (modeName == L"string") return Mode::STRING;
    73 		else if (modeName == L"boolean") return Mode::BOOLEAN;
    73 		else if (modeName == L"boolean") return Mode::BOOLEAN;
    74 		else if (modeName == L"raw-xml") return Mode::RAW_XML;
    74 		else if (modeName == L"raw-xml") return Mode::RAW_XML;
    75 		else if (modeName == L"line-number") return Mode::LINE_NUMBER;
    75 		else if (modeName == L"line-number") return Mode::LINE_NUMBER;
    76 		else if (modeName == L"xpath") return Mode::XPATH;
    76 		else if (modeName == L"xpath") return Mode::XPATH;
    77 		else throw std::invalid_argument("Unsupported mode: " + convertor.to_bytes(modeName));
    77 		else throw std::invalid_argument("Unsupported mode: " + toBytes(modeName));
    78 	}
    78 	}
    79 
    79 
    80 	std::wstring toType(Mode mode) {
    80 	std::wstring toType(Mode mode) {
    81 		if (mode == Mode::BOOLEAN) return BOOLEAN;
    81 		if (mode == Mode::BOOLEAN) return BOOLEAN;
    82 		else if (mode == Mode::LINE_NUMBER) return INTEGER;
    82 		else if (mode == Mode::LINE_NUMBER) return INTEGER;
   116 	std::vector<OutputAttribute> getOutputAttributes() override {
   116 	std::vector<OutputAttribute> getOutputAttributes() override {
   117 		std::vector<OutputAttribute> oa;
   117 		std::vector<OutputAttribute> oa;
   118 
   118 
   119 		try {
   119 		try {
   120 			xmlpp::DomParser parser;
   120 			xmlpp::DomParser parser;
   121 			parser.parse_file(convertor.to_bytes(currentFile));
   121 			parser.parse_file(toBytes(getCurrentFile()));
   122 			xmlpp::Element* root = parser.get_document()->get_root_node();
   122 			xmlpp::Element* root = parser.get_document()->get_root_node();
   123 
   123 
   124 			for (XPathAttribute xpathAttribute : xpathAttributes) {
   124 			for (XPathAttribute xpathAttribute : xpathAttributes) {
   125 				std::string xpath = convertor.to_bytes(xpathAttribute.xpath);
   125 				std::string xpath = toBytes(xpathAttribute.xpath);
   126 				std::wstring result;
   126 				std::wstring result;
   127 				bool isNull = false;
   127 				bool isNull = false;
   128 
   128 
   129 				if (xpathAttribute.mode == Mode::STRING) {
   129 				if (xpathAttribute.mode == Mode::STRING) {
   130 					result = convertor.from_bytes(root->eval_to_string(xpath, ns));
   130 					result = fromBytes(root->eval_to_string(xpath, ns));
   131 				} else if (xpathAttribute.mode == Mode::BOOLEAN) {
   131 				} else if (xpathAttribute.mode == Mode::BOOLEAN) {
   132 					result = root->eval_to_boolean(xpath, ns) ? L"true" : L"false";
   132 					result = root->eval_to_boolean(xpath, ns) ? L"true" : L"false";
   133 				} else if (xpathAttribute.mode == Mode::LINE_NUMBER) {
   133 				} else if (xpathAttribute.mode == Mode::LINE_NUMBER) {
   134 					xmlpp::NodeSet attributeNodes = root->find(xpath, ns);
   134 					xmlpp::NodeSet attributeNodes = root->find(xpath, ns);
   135 					if (attributeNodes.size()) result = std::to_wstring(attributeNodes[0]->get_line());
   135 					if (attributeNodes.size()) result = std::to_wstring(attributeNodes[0]->get_line());
   136 					else isNull = true;
   136 					else isNull = true;
   137 				} else if (xpathAttribute.mode == Mode::XPATH) {
   137 				} else if (xpathAttribute.mode == Mode::XPATH) {
   138 					xmlpp::NodeSet attributeNodes = root->find(xpath, ns);
   138 					xmlpp::NodeSet attributeNodes = root->find(xpath, ns);
   139 					if (attributeNodes.size()) result = convertor.from_bytes(attributeNodes[0]->get_path());
   139 					if (attributeNodes.size()) result = fromBytes(attributeNodes[0]->get_path());
   140 					else isNull = true;
   140 					else isNull = true;
   141 				} else if (xpathAttribute.mode == Mode::RAW_XML) {
   141 				} else if (xpathAttribute.mode == Mode::RAW_XML) {
   142 					throw std::logic_error("Raw XML mode is not yet implemented."); // TODO: implement also RAW_XML
   142 					throw std::logic_error("Raw XML mode is not yet implemented."); // TODO: implement also RAW_XML
   143 				} else {
   143 				} else {
   144 					throw std::logic_error("Unsupported mode."); // should never happer
   144 					throw std::logic_error("Unsupported mode."); // should never happer