Android 读取APK签名信息

来源:互联网 发布:剑网三脸型数据成男 编辑:程序博客网 时间:2024/05/17 03:42
[java] view plaincopy
  1. 某些时候需要获取某个特定的apk(已安装或者未安装)的签名信息,如程序自检测,可信赖的第三方检测(应用市场),系统限定安装  
  2. 对此,有两种实现方法  
  3. 可以使用Java自带的API(主要用到的为JarFile,JarEntry,Certificate)进行获取,还有一种方法是使用系统隐藏的API PackageParser,通过反射来使用对应的API.  
  4. 但是由于安卓系统的分裂版本过多,并且不同厂商进行的修改很多,依赖反射隐藏API的方法并不能保证兼容性和通用性,因此推荐使用JAVA自带API进行获取:  
  5.   
  6.     /** 
  7.      * 从APK中读取签名 
  8.      * @param file 
  9.      * @return 
  10.      * @throws IOException 
  11.      */  
  12.     private static List<String> getSignaturesFromApk(File file) throws IOException {  
  13.         List<String> signatures=new ArrayList<String>();  
  14.         JarFile jarFile=new JarFile(file);  
  15.         try {  
  16.             JarEntry je=jarFile.getJarEntry("AndroidManifest.xml");  
  17.             byte[] readBuffer=new byte[8192];  
  18.             Certificate[] certs=loadCertificates(jarFile, je, readBuffer);  
  19.             if(certs != null) {  
  20.                 for(Certificate c: certs) {  
  21.                     String sig=toCharsString(c.getEncoded());  
  22.                     signatures.add(sig);  
  23.                 }  
  24.             }  
  25.         } catch(Exception ex) {  
  26.         }  
  27.         return signatures;  
  28.     }  



[java] view plaincopy
  1.     /** 
  2.      * 加载签名 
  3.      * @param jarFile 
  4.      * @param je 
  5.      * @param readBuffer 
  6.      * @return 
  7.      */  
  8.     private static Certificate[] loadCertificates(JarFile jarFile, JarEntry je, byte[] readBuffer) {  
  9.         try {  
  10.             InputStream is=jarFile.getInputStream(je);  
  11.             while(is.read(readBuffer, 0, readBuffer.length) != -1) {  
  12.             }  
  13.             is.close();  
  14.             return je != null ? je.getCertificates() : null;  
  15.         } catch(IOException e) {  
  16.         }  
  17.         return null;  
  18.     }  
  19.   
  20.   
  21.   
  22. /** 
  23.      * 将签名转成转成可见字符串 
  24.      * @param sigBytes 
  25.      * @return 
  26.      */  
  27.     private static String toCharsString(byte[] sigBytes) {  
  28.         byte[] sig=sigBytes;  
  29.         final int N=sig.length;  
  30.         final int N2=N * 2;  
  31.         char[] text=new char[N2];  
  32.         for(int j=0; j < N; j++) {  
  33.             byte v=sig[j];  
  34.             int d=(v >> 4) & 0xf;  
  35.             text[j * 2]=(char)(d >= 10 ? ('a' + d - 10) : ('0' + d));  
  36.             d=v & 0xf;  
  37.             text[j * 2 + 1]=(char)(d >= 10 ? ('a' + d - 10) : ('0' + d));  
  38.         }  
  39.         return new String(text);  
  40.     }  
0 0
原创粉丝点击