void SimpleHttpResult::addHeaderField (char const* line, size_t length) { auto find = static_cast<char const*>(memchr(static_cast<void const*>(line), ':', length)); if (find == nullptr) { find = static_cast<char const*>(memchr(static_cast<void const*>(line), ' ', length)); } if (find != nullptr) { size_t l = find - line; addHeaderField(line, l, find + 1, length - l - 1); } }
void SimpleHttpResult::addHeaderField (std::string const& line) { string key; string value; size_t find = line.find(": "); if (find != string::npos) { key = line.substr(0, find); value = StringUtils::trim(line.substr(find + 2)); addHeaderField(key, value); return; } find = line.find(" "); if (find != string::npos) { key = line.substr(0, find); if (find + 1 < line.length()) { value = StringUtils::trim(line.substr(find + 1)); } addHeaderField(key, value); } }
void HttpRequest::calcBody() { if (_is_multipart) { genBoundary(); int length = 0; //计算Content-Length _body.clear(); //添加Fields for (size_t i = 0; i < _body_fields.size(); i++) { const std::string& name = _body_fields[i]._field_name; const std::string& value = _body_fields[i]._field_value; std::string field = "--" + _boundary + "\r\n" + "content-disposition: form-data; name=\"" + name + "\"\r\n\r\n" + value + "\r\n"; _body += field; } length = (int)_body.size(); //添加Files for (size_t i = 0; i < _post_files.size(); i++) { std::string name = _post_files[i]->_name; IHttpPostFile* post_file = _post_files[i]->_post_file; std::string post_part = "--" + _boundary + "\r\n" + "content-disposition: form-data; name=\"" + name + "\"; filename=\"" + post_file->getFilename() + "\"\r\n" + "content-type: " + post_file->getContentType() + "\r\n" + "\r\n"; length += (int)post_part.size(); length += post_file->getFileSize(); length += 2; //在文件后需要添加\r\n } std::string post_end = "--" + _boundary + "--\r\n"; length += (int)post_end.size(); //添加Content-Type和Content-Length字段 std::string content_type = "multipart/form-data; boundary=" + _boundary; addHeaderField(kcontent_type,content_type); std::string content_length = Util::num_to_string(length); addHeaderField(kcontent_length,content_length); } else { //如果没有直接设置Http体,则以Field的形式构造HTTP体 if (_body.empty()) { for (size_t i = 0 ; i < _body_fields.size(); i++) { if (!_body.empty()) { _body += "&"; } const std::string& name = _body_fields[i]._field_name; const std::string& value = _body_fields[i]._field_value; _body += (name + "=" + Util::torfc1738(value)); } addExtraHeaderField(kcontent_type,"application/x-www-form-urlencoded"); } else { addExtraHeaderField(kcontent_type,"text/plain"); } std::string content_length = Util::num_to_string((int)_body.length()); addHeaderField(kcontent_length,content_length); } }
void DataDictionary::readFromDocument( DOMDocumentPtr pDoc ) throw( ConfigError ) { // VERSION DOMNodePtr pFixNode = pDoc->getNode("/fix"); if(!pFixNode.get()) throw ConfigError("Could not parse data dictionary file" ", or no <fix> node found at root"); DOMAttributesPtr attrs = pFixNode->getAttributes(); std::string type = "FIX"; if(attrs->get("type", type)) { if(type != "FIX" && type != "FIXT") throw ConfigError("type attribute must be FIX or FIXT"); } std::string major; if(!attrs->get("major", major)) throw ConfigError("major attribute not found on <fix>"); std::string minor; if(!attrs->get("minor", minor)) throw ConfigError("minor attribute not found on <fix>"); setVersion(type + "." + major + "." + minor); // FIELDS DOMNodePtr pFieldsNode = pDoc->getNode("/fix/fields"); if(!pFieldsNode.get()) throw ConfigError("<fields> section not found in data dictionary"); DOMNodePtr pFieldNode = pFieldsNode->getFirstChildNode(); if(!pFieldNode.get()) throw ConfigError("No fields defined"); while(pFieldNode.get()) { if(pFieldNode->getName() == "field") { DOMAttributesPtr attrs = pFieldNode->getAttributes(); std::string name; if(!attrs->get("name", name)) throw ConfigError("<field> does not have a name attribute"); std::string number; if(!attrs->get("number", number)) throw ConfigError("<field> " + name + " does not have a number attribute"); int num = atol(number.c_str()); std::string type; if(!attrs->get("type", type)) throw ConfigError("<field> " + name + " does not have a type attribute"); addField(num); addFieldType(num, XMLTypeToType(type)); addFieldName(num, name); DOMNodePtr pFieldValueNode = pFieldNode->getFirstChildNode(); while(pFieldValueNode.get()) { if(pFieldValueNode->getName() == "value") { DOMAttributesPtr attrs = pFieldValueNode->getAttributes(); std::string enumeration; if(!attrs->get("enum", enumeration)) throw ConfigError("<value> does not have enum attribute in field " + name); addFieldValue(num, enumeration); std::string description; if(attrs->get("description", description)) addValueName(num, enumeration, description); } RESET_AUTO_PTR(pFieldValueNode, pFieldValueNode->getNextSiblingNode()); } } RESET_AUTO_PTR(pFieldNode, pFieldNode->getNextSiblingNode()); } // HEADER if( type == "FIXT" || (type == "FIX" && major < "5") ) { DOMNodePtr pHeaderNode = pDoc->getNode("/fix/header"); if(!pHeaderNode.get()) throw ConfigError("<header> section not found in data dictionary"); DOMNodePtr pHeaderFieldNode = pHeaderNode->getFirstChildNode(); if(!pHeaderFieldNode.get()) throw ConfigError("No header fields defined"); while(pHeaderFieldNode.get()) { if(pHeaderFieldNode->getName() == "field" || pHeaderFieldNode->getName() == "group" ) { DOMAttributesPtr attrs = pHeaderFieldNode->getAttributes(); std::string name; if(!attrs->get("name", name)) throw ConfigError("<field> does not have a name attribute"); std::string required = "false"; attrs->get("required", required); addHeaderField(lookupXMLFieldNumber(pDoc.get(), name), required == "true"); } if(pHeaderFieldNode->getName() == "group") { DOMAttributesPtr attrs = pHeaderFieldNode->getAttributes(); std::string required; attrs->get("required", required); bool isRequired = (required == "Y" || required == "y"); addXMLGroup(pDoc.get(), pHeaderFieldNode.get(), "_header_", *this, isRequired); } RESET_AUTO_PTR(pHeaderFieldNode, pHeaderFieldNode->getNextSiblingNode()); } } // TRAILER if( type == "FIXT" || (type == "FIX" && major < "5") ) { DOMNodePtr pTrailerNode = pDoc->getNode("/fix/trailer"); if(!pTrailerNode.get()) throw ConfigError("<trailer> section not found in data dictionary"); DOMNodePtr pTrailerFieldNode = pTrailerNode->getFirstChildNode(); if(!pTrailerFieldNode.get()) throw ConfigError("No trailer fields defined"); while(pTrailerFieldNode.get()) { if(pTrailerFieldNode->getName() == "field" || pTrailerFieldNode->getName() == "group" ) { DOMAttributesPtr attrs = pTrailerFieldNode->getAttributes(); std::string name; if(!attrs->get("name", name)) throw ConfigError("<field> does not have a name attribute"); std::string required = "false"; attrs->get("required", required); addTrailerField(lookupXMLFieldNumber(pDoc.get(), name), required == "true"); } if(pTrailerFieldNode->getName() == "group") { DOMAttributesPtr attrs = pTrailerFieldNode->getAttributes(); std::string required; attrs->get("required", required); bool isRequired = (required == "Y" || required == "y"); addXMLGroup(pDoc.get(), pTrailerFieldNode.get(), "_trailer_", *this, isRequired); } RESET_AUTO_PTR(pTrailerFieldNode, pTrailerFieldNode->getNextSiblingNode()); } } // MSGTYPE DOMNodePtr pMessagesNode = pDoc->getNode("/fix/messages"); if(!pMessagesNode.get()) throw ConfigError("<messages> section not found in data dictionary"); DOMNodePtr pMessageNode = pMessagesNode->getFirstChildNode(); if(!pMessageNode.get()) throw ConfigError("No messages defined"); while(pMessageNode.get()) { if(pMessageNode->getName() == "message") { DOMAttributesPtr attrs = pMessageNode->getAttributes(); std::string msgtype; if(!attrs->get("msgtype", msgtype)) throw ConfigError("<field> does not have a name attribute"); addMsgType(msgtype); std::string name; if(attrs->get("name", name)) addValueName( 35, msgtype, name ); DOMNodePtr pMessageFieldNode = pMessageNode->getFirstChildNode(); while( pMessageFieldNode.get() ) { if(pMessageFieldNode->getName() == "field" || pMessageFieldNode->getName() == "group") { DOMAttributesPtr attrs = pMessageFieldNode->getAttributes(); std::string name; if(!attrs->get("name", name)) throw ConfigError("<field> does not have a name attribute"); int num = lookupXMLFieldNumber(pDoc.get(), name); addMsgField(msgtype, num); std::string required; if(attrs->get("required", required) && (required == "Y" || required == "y")) { addRequiredField(msgtype, num); } } else if(pMessageFieldNode->getName() == "component") { DOMAttributesPtr attrs = pMessageFieldNode->getAttributes(); std::string required; attrs->get("required", required); bool isRequired = (required == "Y" || required == "y"); addXMLComponentFields(pDoc.get(), pMessageFieldNode.get(), msgtype, *this, isRequired); } if(pMessageFieldNode->getName() == "group") { DOMAttributesPtr attrs = pMessageFieldNode->getAttributes(); std::string required; attrs->get("required", required); bool isRequired = (required == "Y" || required == "y"); addXMLGroup(pDoc.get(), pMessageFieldNode.get(), msgtype, *this, isRequired); } RESET_AUTO_PTR(pMessageFieldNode, pMessageFieldNode->getNextSiblingNode()); } } RESET_AUTO_PTR(pMessageNode, pMessageNode->getNextSiblingNode()); } }