@@ -2,6 +2,7 @@ package luso_bank | |||||
import ( | import ( | ||||
zhios_pay_utils "code.fnuoos.com/go_rely_warehouse/zyos_go_pay.git/utils" | zhios_pay_utils "code.fnuoos.com/go_rely_warehouse/zyos_go_pay.git/utils" | ||||
"crypto" | |||||
"encoding/base64" | "encoding/base64" | ||||
"fmt" | "fmt" | ||||
"github.com/syyongx/php2go" | "github.com/syyongx/php2go" | ||||
@@ -14,6 +15,7 @@ const ( | |||||
TerminalNo = "98036140" | TerminalNo = "98036140" | ||||
PrivateKeyStr = "-----BEGIN PRIVATE KEY-----\nMIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDSYivjR7nXUazy\nf+F1i/nvuy/doiHRsiTSwavHIwKF88kzM95Eh5wGiXq6TXwFPhB5yeV8l3tFQxeu\nPycZeKmp0VBge+U+/UhR1rQwEX9U9LeKhVdjbNU0U8kNpO8qX/QqHSS7MCRILL2a\nS4F5U/wvYGkbqJ+qMUNmEMGwEkiVuDaO/Q4I3lMPNtLO+mizgq9jggEkVh+xG50p\nFATWd6CJh0mddBBgGG3/aG1ybV/IYRRP0sS+dbYKmKghbK2d/LztIM8ba7lA16H9\nxLY8oy8SvwGqkq2Gea9K2AIEjociac4i0Q/Ka2U881rJCrDUMg3gDhIundaa971M\nglS5cRe9AgMBAAECggEBALe9P6FHIlqYHZjI8QqtToL+E6bYk/rFP/3FYZYQ0IJW\n0NDkKunlGfJnnYUaaQdXFiKXntJ6phFusD7hLu/C/0Kt6Snq6uNhaAj5n/MfRPrY\no3faTuEpyubhigVdl/eFSASD4XGOcRGL6afY6+If5G8oH4QleBS246s/VTnGLhh6\n7cWv2PvFQOU6WzayYzs+8wIYPlVlhKIfuU7vbQF7sWIFfJg8zqVFe2lNXwGS3D2f\ns8AjjN9lMemWF/t9OIA4l9b/Mr2D1wc71AznTUXgBWqm747tWAYyEQ+r1PimbPMB\nEUi6qllpB0qhoEmSVQxONcR3GIep0IwDj8PHQtP55qECgYEA7cnP0yNcc1if7Dd/\nBh0xWGafMVkHIPbbBVOgR3FakaTuC5g0OQ7LP5O8OCW1pchyJY0HXLCEiRVSj5O7\n3MY59eIbdqpcBI7a+ZxOyBHEN2IqZ4EVZmkCxd7w7XA12D+mT19rc//F03FT78e5\neYniSWmj0ku1bSJ7oYb1g4mPf6kCgYEA4n8MKlYIf0JALvMgws78M75JMVpSVgDs\nOngZvMF7z7x4gkBxXxxc5ABe6k/RXCuz59n2IQU3NzS0Y3HxCvZyeJzh1X5ENSdD\nsyJVFkb4oC8nhKvztXT8CwH1vSIGMRUJNE3Gn8IrX8QdEWdvADz/+Iw81HtOh7lr\nAGyreWyLc/UCgYBBFaXuspURdUaAj0gTUlY5Tg1wol+TJD4anSMXqu0RREVrowNY\nQrZa9oLkE14+vDiSEqHbOu1r4AwzBEq9SPyAUp0Vw9df4AILpD7kAAjm59WXcvt6\nhm+d3UGwm7ABOpq4yvNMUsvA7hn9XXtkytrHIUUXwGUuM+wG8Duu/y3p0QKBgQC3\nsZKMQ3pgu7qSWV0YogapcIqsHDTqy5TLVtyI2eMweArEmL9aBAbSY/qWzmVd+5PN\nVljoLvK5M2WZwa9c1MPCTnpaTC3FbjLZ9d5MUwMR5yyFzW+6m0ZPJyfGXPHonMb6\nRJnyt+e1o7hvhRPhfZecXSB4tAjcyuSdU4U+1WnEgQKBgAUZFTYeIyC/bnIca5m8\nzh2wIW0KusCLPa9e3VGTARJG5WP6nx8BPVx71Er/wquBLLquoH0XlTmpdj80QF+s\nHlnKE9CfXVu23ci2S0WalbX/8CYGlO5iCct9o0KR0inrXKfqFzuSKkpg6JyXVMk0\nMT1+EUSD25ATIRsNGFWigNHL\n-----END PRIVATE KEY-----" | PrivateKeyStr = "-----BEGIN PRIVATE KEY-----\nMIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDSYivjR7nXUazy\nf+F1i/nvuy/doiHRsiTSwavHIwKF88kzM95Eh5wGiXq6TXwFPhB5yeV8l3tFQxeu\nPycZeKmp0VBge+U+/UhR1rQwEX9U9LeKhVdjbNU0U8kNpO8qX/QqHSS7MCRILL2a\nS4F5U/wvYGkbqJ+qMUNmEMGwEkiVuDaO/Q4I3lMPNtLO+mizgq9jggEkVh+xG50p\nFATWd6CJh0mddBBgGG3/aG1ybV/IYRRP0sS+dbYKmKghbK2d/LztIM8ba7lA16H9\nxLY8oy8SvwGqkq2Gea9K2AIEjociac4i0Q/Ka2U881rJCrDUMg3gDhIundaa971M\nglS5cRe9AgMBAAECggEBALe9P6FHIlqYHZjI8QqtToL+E6bYk/rFP/3FYZYQ0IJW\n0NDkKunlGfJnnYUaaQdXFiKXntJ6phFusD7hLu/C/0Kt6Snq6uNhaAj5n/MfRPrY\no3faTuEpyubhigVdl/eFSASD4XGOcRGL6afY6+If5G8oH4QleBS246s/VTnGLhh6\n7cWv2PvFQOU6WzayYzs+8wIYPlVlhKIfuU7vbQF7sWIFfJg8zqVFe2lNXwGS3D2f\ns8AjjN9lMemWF/t9OIA4l9b/Mr2D1wc71AznTUXgBWqm747tWAYyEQ+r1PimbPMB\nEUi6qllpB0qhoEmSVQxONcR3GIep0IwDj8PHQtP55qECgYEA7cnP0yNcc1if7Dd/\nBh0xWGafMVkHIPbbBVOgR3FakaTuC5g0OQ7LP5O8OCW1pchyJY0HXLCEiRVSj5O7\n3MY59eIbdqpcBI7a+ZxOyBHEN2IqZ4EVZmkCxd7w7XA12D+mT19rc//F03FT78e5\neYniSWmj0ku1bSJ7oYb1g4mPf6kCgYEA4n8MKlYIf0JALvMgws78M75JMVpSVgDs\nOngZvMF7z7x4gkBxXxxc5ABe6k/RXCuz59n2IQU3NzS0Y3HxCvZyeJzh1X5ENSdD\nsyJVFkb4oC8nhKvztXT8CwH1vSIGMRUJNE3Gn8IrX8QdEWdvADz/+Iw81HtOh7lr\nAGyreWyLc/UCgYBBFaXuspURdUaAj0gTUlY5Tg1wol+TJD4anSMXqu0RREVrowNY\nQrZa9oLkE14+vDiSEqHbOu1r4AwzBEq9SPyAUp0Vw9df4AILpD7kAAjm59WXcvt6\nhm+d3UGwm7ABOpq4yvNMUsvA7hn9XXtkytrHIUUXwGUuM+wG8Duu/y3p0QKBgQC3\nsZKMQ3pgu7qSWV0YogapcIqsHDTqy5TLVtyI2eMweArEmL9aBAbSY/qWzmVd+5PN\nVljoLvK5M2WZwa9c1MPCTnpaTC3FbjLZ9d5MUwMR5yyFzW+6m0ZPJyfGXPHonMb6\nRJnyt+e1o7hvhRPhfZecXSB4tAjcyuSdU4U+1WnEgQKBgAUZFTYeIyC/bnIca5m8\nzh2wIW0KusCLPa9e3VGTARJG5WP6nx8BPVx71Er/wquBLLquoH0XlTmpdj80QF+s\nHlnKE9CfXVu23ci2S0WalbX/8CYGlO5iCct9o0KR0inrXKfqFzuSKkpg6JyXVMk0\nMT1+EUSD25ATIRsNGFWigNHL\n-----END PRIVATE KEY-----" | ||||
MchtStoreNm = "世寶商城" | MchtStoreNm = "世寶商城" | ||||
PUBLICKEY = "-----BEGIN PUBLIC KEY-----\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0mIr40e511Gs8n/hdYv5\n77sv3aIh0bIk0sGrxyMChfPJMzPeRIecBol6uk18BT4QecnlfJd7RUMXrj8nGXip\nqdFQYHvlPv1IUda0MBF/VPS3ioVXY2zVNFPJDaTvKl/0Kh0kuzAkSCy9mkuBeVP8\nL2BpG6ifqjFDZhDBsBJIlbg2jv0OCN5TDzbSzvpos4KvY4IBJFYfsRudKRQE1neg\niYdJnXQQYBht/2htcm1fyGEUT9LEvnW2CpioIWytnfy87SDPG2u5QNeh/cS2PKMv\nEr8BqpKthnmvStgCBI6HImnOItEPymtlPPNayQqw1DIN4A4SLp3Wmve9TIJUuXEX\nvQIDAQAB\n-----END PUBLIC KEY-----" | |||||
) | ) | ||||
type PayParam struct { | type PayParam struct { | ||||
@@ -56,7 +58,7 @@ func (payParam *PayParam) SetData(dataParam DataParam) *signParam { | |||||
func (s *signParam) SetSign(privateKeyStr string) error { | func (s *signParam) SetSign(privateKeyStr string) error { | ||||
dataParamBase64Str := base64.StdEncoding.EncodeToString([]byte(s.PayParam.Data)) | dataParamBase64Str := base64.StdEncoding.EncodeToString([]byte(s.PayParam.Data)) | ||||
signStr, err := zhios_pay_utils.GetSign(privateKeyStr, dataParamBase64Str) | |||||
signStr, err := zhios_pay_utils.GetSignV2(privateKeyStr, dataParamBase64Str, crypto.SHA1) | |||||
if err != nil { | if err != nil { | ||||
return err | return err | ||||
} | } | ||||
@@ -3,6 +3,8 @@ package test | |||||
import ( | import ( | ||||
luso "code.fnuoos.com/go_rely_warehouse/zyos_go_pay.git/lib/luso_bank" | luso "code.fnuoos.com/go_rely_warehouse/zyos_go_pay.git/lib/luso_bank" | ||||
zhios_pay_utils "code.fnuoos.com/go_rely_warehouse/zyos_go_pay.git/utils" | zhios_pay_utils "code.fnuoos.com/go_rely_warehouse/zyos_go_pay.git/utils" | ||||
"crypto" | |||||
"log" | |||||
"testing" | "testing" | ||||
) | ) | ||||
@@ -31,9 +33,20 @@ func TestLusoPay(t *testing.T) { | |||||
if err != nil { | if err != nil { | ||||
t.Error(err) | t.Error(err) | ||||
} | } | ||||
resp, err := client.PayParam.Send(false) | |||||
resp, err := client.PayParam.Send(false, false, "create") | |||||
if err != nil { | if err != nil { | ||||
t.Error(err) | t.Error(err) | ||||
} | } | ||||
t.Logf("回調信息:%s", resp) | t.Logf("回調信息:%s", resp) | ||||
} | } | ||||
func TestRsa2Rsa2PriSign(t *testing.T) { | |||||
//原内容 | |||||
str := "eyJoZWFkIjp7Im1jaHRObyI6IjMwMDExIiwicmVxVGltZSI6IjIwMjIxMTA5MTUwNjQ1IiwibXNnSWQiOiI1MjE0NTAxNjY3OTc3NjA1MzgyMDIyMTEwOTE1MDY0NSIsImF0dGFjaCI6IiIsImNlcnRJZCI6IjAxIiwidmVyc2lvbiI6IjEuMC4wIn0sInJlcUJvZHkiOnsiZXh0TXNnICI6IntcIm1pZFwiOlwiMTIzNDU2XCIsXCJvcmRfdHlwZVwiOlwibWFsbF9nb29kc1wifSIsIm1jaHRPcmRlcklkIjoiNTIxNDUwMTY2Nzk3NzYwNTM4IiwibWRzZURlc2MgIjoi5LiW5a+25ZWG5Z+OLeiHqueHn+izvOeJqSIsIm5vdGlmeVVybCAiOiJodHRwOi8vaW5hcGkuaXpoeWluLmNuOjgwL3BheS9sdXNvL2NhbGxiYWNrIiwicGF5U2NlbmUgIjoiQVNfTVdFQiIsInN1Yk1jaHRObSAiOiLkuJblr7bllYbln44iLCJ0cmFuc0Ftb3VudCAiOiIxMDAuMDAiLCJ0cmFuc0N1ciAiOiJNT1AifX0=" | |||||
//生成签名 | |||||
sig, _ := zhios_pay_utils.GetSignV2(luso.PrivateKeyStr, str, crypto.SHA1) | |||||
log.Println(sig) | |||||
//验证原内容与签名是否一致 | |||||
res := zhios_pay_utils.Rsa2PubCheckSign(str, sig, luso.PUBLICKEY, crypto.SHA1) | |||||
log.Println(res) | |||||
} |
@@ -4,7 +4,11 @@ import ( | |||||
"crypto" | "crypto" | ||||
"crypto/rand" | "crypto/rand" | ||||
"crypto/rsa" | "crypto/rsa" | ||||
"crypto/sha1" | |||||
"crypto/x509" | |||||
"encoding/base64" | "encoding/base64" | ||||
"encoding/pem" | |||||
"errors" | |||||
"fmt" | "fmt" | ||||
"golang.org/x/crypto/ssh" | "golang.org/x/crypto/ssh" | ||||
"sort" | "sort" | ||||
@@ -28,7 +32,49 @@ func GetSign(privateKeyStr, data string) (string, error) { | |||||
return base64.StdEncoding.EncodeToString(sign), nil | return base64.StdEncoding.EncodeToString(sign), nil | ||||
} | } | ||||
//规则: | |||||
func GetSignV2(privateKeyStr, data string, hash crypto.Hash) (string, error) { | |||||
privateKey, err := ssh.ParseRawPrivateKey([]byte(privateKeyStr)) | |||||
if err != nil { | |||||
return "", err | |||||
} | |||||
h := crypto.Hash.New(hash) | |||||
h.Write([]byte(data)) | |||||
hashed := h.Sum(nil) | |||||
sign, err := rsa.SignPKCS1v15(rand.Reader, privateKey.(*rsa.PrivateKey), hash, hashed) | |||||
if err != nil { | |||||
return "", nil | |||||
} | |||||
return base64.StdEncoding.EncodeToString(sign), nil | |||||
} | |||||
// RSA2公钥验证签名 | |||||
func Rsa2PubCheckSign(signContent, sign, publicKey string, hash crypto.Hash) bool { | |||||
hashed := sha1.Sum([]byte(signContent)) | |||||
pubKey, err := ParsePublicKey(publicKey) | |||||
if err != nil { | |||||
return false | |||||
} | |||||
sig, _ := base64.StdEncoding.DecodeString(sign) | |||||
err = rsa.VerifyPKCS1v15(pubKey, hash, hashed[:], sig) | |||||
if err != nil { | |||||
return false | |||||
} | |||||
return true | |||||
} | |||||
// 解析公钥 | |||||
func ParsePublicKey(publicKey string) (*rsa.PublicKey, error) { | |||||
block, _ := pem.Decode([]byte(publicKey)) | |||||
if block == nil { | |||||
return nil, errors.New("公钥信息错误!") | |||||
} | |||||
pubKey, err := x509.ParsePKIXPublicKey(block.Bytes) | |||||
if err != nil { | |||||
return nil, err | |||||
} | |||||
return pubKey.(*rsa.PublicKey), nil | |||||
} | |||||
//◆ 参数名ASCII码从小到大排序(字典序); | //◆ 参数名ASCII码从小到大排序(字典序); | ||||
//◆ 如果参数的值为空不参与签名; | //◆ 如果参数的值为空不参与签名; | ||||
//◆ 参数名区分大小写; | //◆ 参数名区分大小写; | ||||