Android 获取签名公钥和公钥私钥加解密的方法(推荐)

所属分类: 软件编程 / Android 阅读数: 23
收藏 0 赞 0 分享

如下所示:

public class GetPublicKey {
   
  /**
   * 获取签名公钥
   * @param mContext
   * @return
   */
  protected static String getSignInfo(Context mContext) {
    String signcode = "";
    try {
      PackageInfo packageInfo = mContext.getPackageManager().getPackageInfo(
          GetAppInfo.getPackageName(mContext), PackageManager.GET_SIGNATURES);
      Signature[] signs = packageInfo.signatures;
      Signature sign = signs[0];
 
      signcode = parseSignature(sign.toByteArray());
      signcode = signcode.toLowerCase();
    } catch (Exception e) {
      Log.e(Constants.TAG, e.getMessage(), e);
    }
    return signcode;
  }
 
  protected static String parseSignature(byte[] signature) {
    String sign = "";
    try {
      CertificateFactory certFactory = CertificateFactory
          .getInstance("X.509");
      X509Certificate cert = (X509Certificate) certFactory
          .generateCertificate(new ByteArrayInputStream(signature));
      String pubKey = cert.getPublicKey().toString();
      String ss = subString(pubKey);
      ss = ss.replace(",", "");
      ss = ss.toLowerCase();
      int aa = ss.indexOf("modulus");
      int bb = ss.indexOf("publicexponent");
      sign = ss.substring(aa + 8, bb);
    } catch (CertificateException e) {
      Log.e(Constants.TAG, e.getMessage(), e);
    }
    return sign;
  }
 
  public static String subString(String sub) {
    Pattern pp = Pattern.compile("\\s*|\t|\r|\n");
    Matcher mm = pp.matcher(sub);
    return mm.replaceAll("");
  }
}



package com.example.xscamera;
 
import java.io.ByteArrayOutputStream;
import java.security.Key;
import java.security.KeyFactory;
import java.security.KeyPair;
import java.security.KeyPairGenerator;
import java.security.PrivateKey;
import java.security.PublicKey;
import java.security.Signature;
import java.security.interfaces.RSAPrivateKey;
import java.security.interfaces.RSAPublicKey;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.X509EncodedKeySpec;
import java.util.HashMap;
import java.util.Map;

import javax.crypto.Cipher;
 
/**
 * <p>
 * RSA公钥/私钥/签名工具包
 * <p>
 * 字符串格式的密钥在未在特殊说明情况下都为BASE64编码格式<br/>
 * 由于非对称加密速度极其缓慢,一般文件不使用它来加密而是使用对称加密,<br/>
 * 非对称加密算法可以用来对对称加密的密钥加密,这样保证密钥的安全也就保证了数据的安全
 * </p>
 * 
 */
public class RSAUtils{
 
  /**
   * 加密算法RSA
   */
  public static final String KEY_ALGORITHM = "RSA";
   
  /**
   * 签名算法
   */
  public static final String SIGNATURE_ALGORITHM = "MD5withRSA";
 
  /**
   * 获取公钥的key
   */
  private static final String PUBLIC_KEY = "LocatorPublicKey";
   
  /**
   * 获取私钥的key
   */
  private static final String PRIVATE_KEY = "LocatorPrivateKey";
   
  /**
   * RSA最大加密明文大小
   */
  private static final int MAX_ENCRYPT_BLOCK = 117;
   
  /**
   * RSA最大解密密文大小
   */
  private static final int MAX_DECRYPT_BLOCK = 128;
 
  /**
   * <p>
   * 生成密钥对(公钥和私钥)
   * </p>
   * 
   * @return
   * @throws Exception
   */
  public static Map<String, Object> genKeyPair() throws Exception {
    KeyPairGenerator keyPairGen = KeyPairGenerator.getInstance(KEY_ALGORITHM);
    keyPairGen.initialize(1024);
    KeyPair keyPair = keyPairGen.generateKeyPair();
    RSAPublicKey publicKey = (RSAPublicKey) keyPair.getPublic();
    RSAPrivateKey privateKey = (RSAPrivateKey) keyPair.getPrivate();
    Map<String, Object> keyMap = new HashMap<String, Object>(2);
    keyMap.put(PUBLIC_KEY, publicKey);
    keyMap.put(PRIVATE_KEY, privateKey);
    return keyMap;
  }
   
  /**
   * <p>
   * 用私钥对信息生成数字签名
   * </p>
   * 
   * @param data 已加密数据
   * @param privateKey 私钥(BASE64编码)
   * 
   * @return
   * @throws Exception
   */
  public static String sign(byte[] data, String privateKey) throws Exception {
    byte[] keyBytes = Base64Utils.decode(privateKey);
    PKCS8EncodedKeySpec pkcs8KeySpec = new PKCS8EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
    PrivateKey privateK = keyFactory.generatePrivate(pkcs8KeySpec);
    Signature signature = Signature.getInstance(SIGNATURE_ALGORITHM);
    signature.initSign(privateK);
    signature.update(data);
    return Base64Utils.encode(signature.sign());
  }
 
  /**
   * <p>
   * 校验数字签名
   * </p>
   * 
   * @param data 已加密数据
   * @param publicKey 公钥(BASE64编码)
   * @param sign 数字签名
   * 
   * @return
   * @throws Exception
   * 
   */
  public static boolean verify(byte[] data, String publicKey, String sign)
      throws Exception {
    byte[] keyBytes = Base64Utils.decode(publicKey);
    X509EncodedKeySpec keySpec = new X509EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
    PublicKey publicK = keyFactory.generatePublic(keySpec);
    Signature signature = Signature.getInstance(SIGNATURE_ALGORITHM);
    signature.initVerify(publicK);
    signature.update(data);
    return signature.verify(Base64Utils.decode(sign));
  }
 
  /**
   * <P>
   * 私钥解密
   * </p>
   * 
   * @param encryptedData 已加密数据
   * @param privateKey 私钥(BASE64编码)
   * @return
   * @throws Exception
   */
  public static byte[] decryptByPrivateKey(byte[] encryptedData, String privateKey)
      throws Exception {
    byte[] keyBytes = Base64Utils.decode(privateKey);
    PKCS8EncodedKeySpec pkcs8KeySpec = new PKCS8EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
    Key privateK = keyFactory.generatePrivate(pkcs8KeySpec);
    Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
    cipher.init(Cipher.DECRYPT_MODE, privateK);
    int inputLen = encryptedData.length;
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    int offSet = 0;
    byte[] cache;
    int i = 0;
    // 对数据分段解密
    while (inputLen - offSet > 0) {
      if (inputLen - offSet > MAX_DECRYPT_BLOCK) {
        cache = cipher.doFinal(encryptedData, offSet, MAX_DECRYPT_BLOCK);
      } else {
        cache = cipher.doFinal(encryptedData, offSet, inputLen - offSet);
      }
      out.write(cache, 0, cache.length);
      i++;
      offSet = i * MAX_DECRYPT_BLOCK;
    }
    byte[] decryptedData = out.toByteArray();
    out.close();
    return decryptedData;
  }
 
  /**
   * <p>
   * 公钥解密
   * </p>
   * 
   * @param encryptedData 已加密数据
   * @param publicKey 公钥(BASE64编码)
   * @return
   * @throws Exception
   */
  public static byte[] decryptByPublicKey(byte[] encryptedData, String publicKey)
      throws Exception {
    byte[] keyBytes = Base64Utils.decode(publicKey);
    X509EncodedKeySpec x509KeySpec = new X509EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
    Key publicK = keyFactory.generatePublic(x509KeySpec);
    Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
    cipher.init(Cipher.DECRYPT_MODE, publicK);
    int inputLen = encryptedData.length;
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    int offSet = 0;
    byte[] cache;
    int i = 0;
    // 对数据分段解密
    while (inputLen - offSet > 0) {
      if (inputLen - offSet > MAX_DECRYPT_BLOCK) {
        cache = cipher.doFinal(encryptedData, offSet, MAX_DECRYPT_BLOCK);
      } else {
        cache = cipher.doFinal(encryptedData, offSet, inputLen - offSet);
      }
      out.write(cache, 0, cache.length);
      i++;
      offSet = i * MAX_DECRYPT_BLOCK;
    }
    byte[] decryptedData = out.toByteArray();
    out.close();
    return decryptedData;
  }
 
  /**
   * <p>
   * 公钥加密
   * </p>
   * 
   * @param data 源数据
   * @param publicKey 公钥(BASE64编码)
   * @return
   * @throws Exception
   */
  public static byte[] encryptByPublicKey(byte[] data, String publicKey)
      throws Exception {
    byte[] keyBytes = Base64Utils.decode(publicKey);
    X509EncodedKeySpec x509KeySpec = new X509EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
    Key publicK = keyFactory.generatePublic(x509KeySpec);
    // 对数据加密
    Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
    cipher.init(Cipher.ENCRYPT_MODE, publicK);
    int inputLen = data.length;
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    int offSet = 0;
    byte[] cache;
    int i = 0;
    // 对数据分段加密
    while (inputLen - offSet > 0) {
      if (inputLen - offSet > MAX_ENCRYPT_BLOCK) {
        cache = cipher.doFinal(data, offSet, MAX_ENCRYPT_BLOCK);
      } else {
        cache = cipher.doFinal(data, offSet, inputLen - offSet);
      }
      out.write(cache, 0, cache.length);
      i++;
      offSet = i * MAX_ENCRYPT_BLOCK;
    }
    byte[] encryptedData = out.toByteArray();
    out.close();
    return encryptedData;
  }
 
  /**
   * <p>
   * 私钥加密
   * </p>
   * 
   * @param data 源数据
   * @param privateKey 私钥(BASE64编码)
   * @return
   * @throws Exception
   */
  public static byte[] encryptByPrivateKey(byte[] data, String privateKey)
      throws Exception {
    byte[] keyBytes = Base64Utils.decode(privateKey);
    PKCS8EncodedKeySpec pkcs8KeySpec = new PKCS8EncodedKeySpec(keyBytes);
    KeyFactory keyFactory = KeyFactory.getInstance(KEY_ALGORITHM);
    Key privateK = keyFactory.generatePrivate(pkcs8KeySpec);
    Cipher cipher = Cipher.getInstance(keyFactory.getAlgorithm());
    cipher.init(Cipher.ENCRYPT_MODE, privateK);
    int inputLen = data.length;
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    int offSet = 0;
    byte[] cache;
    int i = 0;
    // 对数据分段加密
    while (inputLen - offSet > 0) {
      if (inputLen - offSet > MAX_ENCRYPT_BLOCK) {
        cache = cipher.doFinal(data, offSet, MAX_ENCRYPT_BLOCK);
      } else {
        cache = cipher.doFinal(data, offSet, inputLen - offSet);
      }
      out.write(cache, 0, cache.length);
      i++;
      offSet = i * MAX_ENCRYPT_BLOCK;
    }
    byte[] encryptedData = out.toByteArray();
    out.close();
    return encryptedData;
  }
 
  /**
   * <p>
   * 获取私钥
   * </p>
   * 
   * @param keyMap 密钥对
   * @return
   * @throws Exception
   */
  public static String getPrivateKey(Map<String, Object> keyMap)
      throws Exception {
    Key key = (Key) keyMap.get(PRIVATE_KEY);
    return Base64Utils.encode(key.getEncoded());
  }
 
  /**
   * <p>
   * 获取公钥
   * </p>
   * 
   * @param keyMap 密钥对
   * @return
   * @throws Exception
   */
  public static String getPublicKey(Map<String, Object> keyMap)
      throws Exception {
    Key key = (Key) keyMap.get(PUBLIC_KEY);
    return Base64Utils.encode(key.getEncoded());
  }
 
}

以上这篇Android 获取签名公钥和公钥私钥加解密的方法(推荐)就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持脚本之家。

更多精彩内容其他人还在看

Android中加入名片扫描功能实例代码

这篇文章主要介绍了Android中加入名片扫描功能实例代码的相关资料,需要的朋友可以参考下
收藏 0 赞 0 分享

Android仿微信发表说说实现拍照、多图上传功能

这篇文章主要为大家详细介绍了Android仿微信发表说说实现拍照、多图上传功能,使用Retrofit2.0技术,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
收藏 0 赞 0 分享

设置Android系统永不锁屏永不休眠的方法

在进行Android系统开发的时候,有些特定的情况需要设置系统永不锁屏,永不休眠。本篇文章给大家介绍Android 永不锁屏,开机不锁屏,删除设置中休眠时间选项,需要的朋友一起学习吧
收藏 0 赞 0 分享

Android Retrofit 2.0框架上传图片解决方案

这篇文章主要介绍了Android Retrofit 2.0框架上传一张与多张图片解决方案,感兴趣的小伙伴们可以参考一下
收藏 0 赞 0 分享

Android自定义等待对话框

这篇文章主要为大家详细介绍了Android自定义等待对话框的实现方法,感兴趣的小伙伴们可以参考一下
收藏 0 赞 0 分享

Android中Window添加View的底层原理

这篇文章主要介绍了Android中Window添加View的底层原理,需要的朋友可以参考下
收藏 0 赞 0 分享

Android调用系统默认浏览器访问的方法

这篇文章主要介绍了Android调用系统默认浏览器访问的方法的相关资料,需要的朋友可以参考下
收藏 0 赞 0 分享

Android开发退出程序的方法汇总

Android程序有很多Activity,比如说主窗口A,调用了子窗口B,子窗口B又调用子窗口C,back返回子窗口B后,在B中如何关闭整个Android应用程序呢? 下面脚本之家小编就给大家介绍android开发退出程序的几种方法,感兴趣的朋友参考下吧
收藏 0 赞 0 分享

Android程序开发中单选按钮(RadioGroup)的使用详解

在android程序开发中,无论是单选按钮还是多选按钮都非常的常见,接下来通过本文给大家介绍Android程序开发中单选按钮(RadioGroup)的使用,需要的朋友参考下吧
收藏 0 赞 0 分享

Android实现仿网易今日头条等自定义频道listview 或者grideview等item上移到另一个view中

这篇文章主要介绍了Android实现仿网易今日头条等自定义频道listview 或者grideview等item上移到另一个view中 的相关资料,需要的朋友可以参考下
收藏 0 赞 0 分享
查看更多