123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566 |
- #include "StdAfx.h"
- #include "PayApi.h"
- #include <algorithm>
- #include "EncodingConversion.h"
- const string Alipay_default_charset = "utf-8";
- const string Alipay_default_url = "https://openapi.alipay.com/gateway.do";
- const string Alipay_default_sign_type = "RSA";
- const string Alipay_default_version = "1.0";
- const string Alipay_appid = "app_id";
- const string Alipay_method = "method";
- const string Alipay_charset = "charset";
- const string Alipay_signtype = "sign_type";
- const string Alipay_sign = "sign";
- const string Alipay_timestamp = "timestamp";
- const string Alipay_version = "version";
- const string Alipay_bizcontenr = "biz_content";
- PayApi::PayApi(void)
- {
- }
- PayApi::~PayApi(void)
- {
- }
- string PayApi::base64Encode(const unsigned char *bytes, int len)
- {
- BIO *bmem = NULL;
- BIO *b64 = NULL;
- BUF_MEM *bptr = NULL;
- b64 = BIO_new(BIO_f_base64());
- BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
- bmem = BIO_new(BIO_s_mem());
- b64 = BIO_push(b64, bmem);
- BIO_write(b64, bytes, len);
- BIO_flush(b64);
- BIO_get_mem_ptr(b64, &bptr);
- string str = string(bptr->data, bptr->length);
- BIO_free_all(b64);
- return str;
- }
- bool PayApi::base64Decode(const string &str, unsigned char *bytes, int &len)
- {
- const char *cstr = str.c_str();
- BIO *bmem = NULL;
- BIO *b64 = NULL;
- b64 = BIO_new(BIO_f_base64());
- BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
- bmem = BIO_new_mem_buf((void *)cstr, strlen(cstr));
- b64 = BIO_push(b64, bmem);
- len = BIO_read(b64, bytes, len);
- BIO_free_all(b64);
- return len > 0;
- }
- string PayApi::rsaSign(const string &content, const string &key)
- {
- string signed_str;
- const char *key_cstr = key.c_str();
- int key_len = strlen(key_cstr);
- BIO *p_key_bio = BIO_new_mem_buf((void *)key_cstr, key_len);
- RSA *p_rsa = PEM_read_bio_RSAPrivateKey(p_key_bio, NULL, NULL, NULL);
- if (p_rsa != NULL) {
- const char *cstr = content.c_str();
- unsigned char hash[SHA_DIGEST_LENGTH] = { 0 };
- SHA1((unsigned char *)cstr, strlen(cstr), hash);
- unsigned char sign[XRSA_KEY_BITS / 8] = { 0 };
- unsigned int sign_len = sizeof(sign);
- int r = RSA_sign(NID_sha1, hash, SHA_DIGEST_LENGTH, sign, &sign_len, p_rsa);
- if (0 != r && sizeof(sign) == sign_len) {
- signed_str = base64Encode(sign, sign_len);
- }
- }
- RSA_free(p_rsa);
- BIO_free(p_key_bio);
- return signed_str;
- }
- bool PayApi::rsaVerify(const string &content, const string &sign, const string &key)
- {
- bool result = false;
- const char *key_cstr = key.c_str();
- int key_len = strlen(key_cstr);
- BIO *p_key_bio = BIO_new_mem_buf((void *)key_cstr, key_len);
- RSA *p_rsa = PEM_read_bio_RSA_PUBKEY(p_key_bio, NULL, NULL, NULL);
- if (p_rsa != NULL) {
- const char *cstr = content.c_str();
- unsigned char hash[SHA_DIGEST_LENGTH] = { 0 };
- SHA1((unsigned char *)cstr, strlen(cstr), hash);
- unsigned char sign_cstr[XRSA_KEY_BITS / 8] = { 0 };
- int len = XRSA_KEY_BITS / 8;
- base64Decode(sign, sign_cstr, len);
- unsigned int sign_len = XRSA_KEY_BITS / 8;
- int r = RSA_verify(NID_sha1, hash, SHA_DIGEST_LENGTH, (unsigned char *)sign_cstr, sign_len, p_rsa);
- if (r > 0) {
- result = true;
- }
- }
- RSA_free(p_rsa);
- BIO_free(p_key_bio);
- return result;
- }
- void PayApi::alipay_setCommonParam( const string &appid, const string &privatekey, const string &signtype, const string &charset, const string &version, const string &url, const string &publickey )
- {
- alipay_appid = appid;
- alipay_privatekey = privatekey;
- alipay_signtype = signtype;
- alipay_charset = charset;
- alipay_version = version;
- alipay_url = url;
- alipay_PublicKey = publickey;
- }
- string PayApi::buildContent(const StringMap &contentPairs)
- {
- string content;
- for (StringMap::const_iterator iter = contentPairs.begin();
- iter != contentPairs.end(); ++iter) {
- if (!content.empty()) {
- content.push_back('&');
- }
- content.append(iter->first);
- content.push_back('=');
- content.append(iter->second);
- }
- return content;
- }
- string PayApi::alipay_invoke(const string & method, const JsonMap & contentMap, const StringMap & extendParamMap)
- {
- string content = JsonUtil::objectToString(JsonType(contentMap));
- return alipay_invoke(method, content, extendParamMap);
- }
- JsonMap PayApi::alipay_Str2JsonMap(string strJson)
- {
-
- int beg = strJson.find("_response\"");
- int end = strJson.rfind("\"sign\"");
- if (beg < 0 || end < 0)
- {
- JsonType jsonObj = JsonUtil::stringToObject(strJson);
- return jsonObj.toMap();
- }
- beg = strJson.find('{', beg);
- end = strJson.rfind('}', end);
- strJson = strJson.substr(beg, end - beg + 1);
- JsonType jsonObj = JsonUtil::stringToObject(strJson);
- return jsonObj.toMap();
- }
- string PayApi::alipay_invoke(const string & method, const string & content, const StringMap & extendParamMap)
- {
-
- time_t t = time(0);
- char tmp[64];
- strftime(tmp, sizeof(tmp), "%Y-%m-%d %X", localtime(&t));
-
- StringMap requestPairs;
- requestPairs.insert(StringMap::value_type(Alipay_appid, alipay_appid));
- requestPairs.insert(StringMap::value_type(Alipay_bizcontenr, content));
- requestPairs.insert(StringMap::value_type(Alipay_charset, alipay_charset));
- requestPairs.insert(StringMap::value_type(Alipay_method, method));
- requestPairs.insert(StringMap::value_type(Alipay_signtype, alipay_signtype));
- requestPairs.insert(StringMap::value_type(Alipay_timestamp, tmp));
- requestPairs.insert(StringMap::value_type(Alipay_version, alipay_version));
-
- for (StringMap::const_iterator iter = extendParamMap.begin(); iter != extendParamMap.end(); ++iter) {
- requestPairs.insert(StringMap::value_type(iter->first, iter->second));
- }
- string wholeContent = buildContent(requestPairs);
- string sign = rsaSign(wholeContent, alipay_privatekey);
- requestPairs.insert(StringMap::value_type(Alipay_sign, sign));
- wholeContent = buildContent(requestPairs);
- #ifdef _DEBUG
- WriteTextLog("\r\nRequest:%s\r\n", wholeContent.c_str());
- #endif
- HttpClient httpClient;
- string responseStr = httpClient.sendSyncRequest(alipay_url, requestPairs);
- #ifdef _DEBUG
- WriteTextLog("\r\nResponse:%s\r\n", responseStr.c_str());
- #endif
-
-
-
- return responseStr;
- }
- string PayApi::analyzeAliResponse(const string & responseStr)
- {
- JsonType responseObj = JsonUtil::stringToObject(responseStr);
- JsonMap responseMap = responseObj.toMap();
-
- int beg = responseStr.find("_response\"");
- int end = responseStr.rfind("\"sign\"");
- if (beg < 0 || end < 0)
- {
- return string();
- }
- beg = responseStr.find('{', beg);
- end = responseStr.rfind('}', end);
-
-
-
-
-
- string responseContent = responseStr.substr(beg, end - beg + 1);
- DebugLog("ResponseContent:%s", responseContent.c_str());
-
-
-
- if (!alipay_PublicKey.empty())
- {
- DebugLog("AlipayPublicKey:%s", alipay_PublicKey.c_str());
- JsonMap::const_iterator iter = responseMap.find(Alipay_sign);
- if (iter == responseMap.end())
- {
- DebugLog("Cannot get Sign from response, Verify Failed");
- return string();
- }
-
- string responseSign = iter->second.toString();
- DebugLog("ResponseSign:%s", responseSign.c_str());
-
- bool verifyResult = rsaVerify(responseContent, responseSign, alipay_PublicKey);
- if (!verifyResult) {
- DebugLog("Verify Failed");
- return string();
- }
- DebugLog("Verify Success");
- }
- else
- {
- DebugLog("AlipayPublicKey is empty, Skip the Verify");
- }
- return responseContent;
- }
- void PayApi::wxpay_setCommonParam(const string & appid, const string & mchid, const string & privatekey)
- {
- wxpay_appid = appid;
- wxpay_mchid = mchid;
- wxpay_privatekey = privatekey;
- }
- string PayApi::wxapi_getSign(StringMap &strMap, string key)
- {
- string strtemp;
- vector<string> vtString;
- for (StringMap::const_iterator iter = strMap.begin(); iter != strMap.end(); iter++)
- {
- if ( _tcscmp(iter->first.c_str(), "sign") != 0 && iter->second.size() != 0 )
- {
- strtemp = iter->first;
- strtemp.append("=");
- strtemp.append(iter->second);
- vtString.push_back(strtemp);
- }
- }
- strtemp.clear();
- std::sort(vtString.begin(), vtString.end());
- for (vector<string>::iterator it = vtString.begin(); it != vtString.end(); it++ )
- {
- strtemp.append(it->c_str());
- strtemp.append("&");
- }
- strtemp.append("key=");
- strtemp.append(key);
- #ifdef _DEBUG
- WriteTextLog("合并:%s\n", strtemp.c_str());
- #endif
-
- EncodingConverion::ASCII2UTF8(strtemp.c_str(), strtemp);
-
- MD5_CTX ctx;
- char sztmp[3] = {0};
- unsigned char szmd[16] = {0};
- MD5_Init(&ctx);
- MD5_Update(&ctx, strtemp.data(), strtemp.size());
- MD5_Final(szmd, &ctx);
- strtemp.clear();
- for ( int i = 0; i < 16; i++ )
- {
- sprintf_s(sztmp, "%02X", szmd[i]);
- strtemp.append(sztmp);
- }
- #ifdef _DEBUG
- WriteTextLog("MD5:%s\n", strtemp.c_str());
- #endif
- return strtemp;
- }
- string PayApi::wxpay_invoke(const string &method, StringMap &extendParamMap, string key )
- {
-
- string sign = wxapi_getSign(extendParamMap, key);
-
- extendParamMap.insert(StringMap::value_type("sign", sign));
- tinyxml2::XMLDocument doc;
- tinyxml2::XMLNode *node = doc.InsertEndChild(doc.NewElement("xml"));
- tinyxml2::XMLElement *subelement = NULL;
- for (StringMap::const_iterator iter = extendParamMap.begin(); iter != extendParamMap.end(); ++iter)
- {
- subelement = doc.NewElement(iter->first.c_str());
- subelement->SetText(iter->second.c_str());
- node->InsertEndChild(subelement);
- }
- tinyxml2::XMLPrinter printer;
- doc.Print(&printer);
- string result = printer.CStr();
- EncodingConverion::ASCII2UTF8(result.c_str(), result);
- HttpClient httpClient;
- string responseStr = httpClient.sendSyncRequest(method, result);
- EncodingConverion::UTF82ASCII(responseStr.c_str(), responseStr);
- #ifdef _DEBUG
- WriteTextLog("返回码:%s\n", responseStr.c_str());
- #endif
- DebugLog("Response:%s", responseStr.c_str());
- return responseStr;
- }
- string PayApi::analyzeWXRespone(const string &respone)
- {
- return "";
- }
|