# Introduction
# Developers can operate by adding a signature. After the signature is generated, the developer can compare it with the information generated by the request in his own code to know whether the data is correct.
# Illustrate:
- The process and method of signature with PayCools are mainly introduced here.
# Signature process
Get the request parameters that need to be encrypted, excluding byte type parameters, such as files and byte streams, remove the sign field, and remove the parameters whose value is empty (Both of null and empty);
Sort in ascending order according to the key value ASCII code of the first character (in ascending alphabetical order), if the same character is encountered, it will sort in ascending order according to the key value ASCII code of the second character, and so on;
Combine the sorted parameters and their corresponding values into the format of parameter=parameter value, and connect these parameters with the & character. At this time, the generated string is the string to be signed.
# Signature original string example
# reqeust body
{
"amount": 100.00,
"appId": "f90addc4861540ef9312e87d8f360e08",
"version":"1.0"
}
#step 2 sign origin string
amount=100.00&appId=f90addc4861540ef9312e87d8f360e08&version=1.0
# Generate signature
- Sign the signature string with the merchant's private key
- Key length is RSA2 4096 bits
- For related code examples, please refer to the following encrypted java demo
public class SignRSAUtils {
protected static final Logger LOGGER = LoggerFactory.getLogger(SignRSAUtils.class);
/**
* Signature algorithm
*/
public static final String SIGN_ALGORITHMS = "SHA1WithRSA";
/**
* RSA signature
*
* @param content data to be signed
* @param privateKey Merchant private key
* @param encode character set encoding
* @return signature value
*/
public static String sign(String content, String privateKey, String encode) {
try {
privateKey = privateKey
.replace("-----BEGIN PRIVATE KEY-----", "")
.replace("-----END PRIVATE KEY-----", "")
.replace("-----BEGIN ENCRYPTED PRIVATE KEY-----", "")
.replace("-----END ENCRYPTED PRIVATE KEY-----", "")
.replace("\r", "")
.replace("\n", "")
.trim();
PKCS8EncodedKeySpec priPKCS8 = new PKCS8EncodedKeySpec(Base64.decode(privateKey));
KeyFactory keyf = KeyFactory.getInstance("RSA");
PrivateKey priKey = keyf.generatePrivate(priPKCS8);
java.security.Signature signature = java.security.Signature.getInstance(SIGN_ALGORITHMS);
signature.initSign(priKey);
signature.update(content.getBytes(encode));
byte[] signed = signature.sign();
return Base64.encode(signed);
} catch (Exception e) {
LOGGER.error("RSA create sign error => exception:", e);
}
return null;
}
/**
* RSA signature
* @param content data to be signed
* @param privateKey signature key
* @return String signature value
*/
public static String sign(String content, String privateKey) {
try {
privateKey = privateKey
.replace("-----BEGIN PRIVATE KEY-----", "")
.replace("-----END PRIVATE KEY-----", "")
.replace("-----BEGIN ENCRYPTED PRIVATE KEY-----", "")
.replace("-----END ENCRYPTED PRIVATE KEY-----", "")
.replace("\r", "")
.replace("\n", "")
.trim();
PKCS8EncodedKeySpec priPKCS8 = new PKCS8EncodedKeySpec(Base64.decode(privateKey));
KeyFactory keyf = KeyFactory.getInstance("RSA");
PrivateKey priKey = keyf.generatePrivate(priPKCS8);
java.security.Signature signature = java.security.Signature.getInstance(SIGN_ALGORITHMS);
signature.initSign(priKey);
signature.update(content.getBytes());
byte[] signed = signature.sign();
return Base64.encode(signed);
} catch (Exception e) {
LOGGER.error("RSA create sign error => exception:", e);
}
return null;
}
/**
* RSA verification signature check
*
* @param content data to be signed
* @param sign signature value
* @param publicKey assigned to the developer public key
* @param encode character set encoding
* @return boolean
*/
public static boolean verifySign(String content, String sign, String publicKey, String encode) {
try {
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
publicKey = publicKey.replace("-----BEGIN PUBLIC KEY-----", "")
.replace("-----END PUBLIC KEY-----", "")
.replace("\r", "")
.replace("\n", "")
.trim();
byte[] encodedKey = Base64.decode(publicKey);
PublicKey pubKey = keyFactory.generatePublic(new X509EncodedKeySpec(encodedKey));
java.security.Signature signature = java.security.Signature
.getInstance(SIGN_ALGORITHMS);
signature.initVerify(pubKey);
signature.update(content.getBytes(encode));
boolean bverify = signature.verify(Base64.decode(sign));
return bverify;
} catch (Exception e) {
LOGGER.error("RSA verify sign error => exception:", e);
}
return false;
}
/**
* RSA verification signature check
*
* @param content data to be signed
* @param sign signature value
* @param publicKey assigned to the developer public key
* @return boolean
*/
public static boolean verifySign(String content, String sign, String publicKey) {
try {
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
publicKey = publicKey.replace("-----BEGIN PUBLIC KEY-----", "")
.replace("-----END PUBLIC KEY-----", "")
.replace("\r", "")
.replace("\n", "")
.trim();
byte[] encodedKey = Base64.decode(publicKey);
PublicKey pubKey = keyFactory.generatePublic(new X509EncodedKeySpec(encodedKey));
java.security.Signature signature = java.security.Signature
.getInstance(SIGN_ALGORITHMS);
signature.initVerify(pubKey);
signature.update(content.getBytes());
return signature.verify(Base64.decode(sign));
} catch (Exception e) {
LOGGER.error("RSA verify sign error => exception:", e);
}
return false;
}
}