批量检查APK是否具有指定的权限。
为测试组的妹子提供的。
效果如下:

目录结构如下:

源代码思路:
1、将apk文件变为zip文件。这里是修改后缀
2、解压文件到指定目录。可以只解压其中mainfest.xml文件
3、移动xml文件到反编译的工具目录下。运行Bat将二进制xml转为txt文本
4、读取配置文件,比对字符串,得出你想要的结果。
具体代码,请去下载工程吧。
部分代码:
package com.wuwenfu; import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Properties; public class FileUtils { // 修改apk为zip
/**
* @author Administrator
* @param apk文件路径
* c:\\1.apk
* @param zip文件保存的路径
* 如c:\\1
* @param b
* 源文件是否删除。false表示不删除 true 表示删除
* @return 返回zip文件的路径
*
*/
public static String apkToZip(String apkPath, String zipPath, Boolean b) {
// TODO Auto-generated method stub
File apk = new File(apkPath); // 获取apk文件的名字。去掉后缀。作为zip文件名
String apkName = apk.getName();
int p = apkName.indexOf(".apk");
String zipName = apkName.substring(0, p) + ".zip"; File zip = new File(zipPath + File.separatorChar + zipName); // 检查文件是否存在、存在则删除
if (zip.exists()) {
zip.delete();
} if (b) {
// 重命名
apk.renameTo(zip);
} else {
// 读取文件 到另一个文件
FileInputStream fis = null;
FileOutputStream fos = null; try {
fis = new FileInputStream(apk);
fos = new FileOutputStream(zip);
int c = 0;
byte[] bys = new byte[1024]; while ((c = fis.read(bys)) != -1) {
// fos.write(bys);
fos.write(bys, 0, c);
fos.flush();
} } catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
fos.close();
fis.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} } return zip.getAbsolutePath(); } /**
* @description 移动文件到指定路径.是剪切操作
* @param 源文件的路径
* c:\\1.txt
* @param 指定的目录
* c:\\1
*/
public static void moveTo(String from, String to) {
// TODO Auto-generated method stub
File fromF = new File(from);
String toName = to + File.separatorChar + fromF.getName();
File toF = new File(toName);
fromF.renameTo(toF); } public static void log(String logPath, String logstr) {
File f = new File(logPath);
FileOutputStream fos = null; try {
fos = new FileOutputStream(f, true);
try {
fos.write(logstr.getBytes());
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
fos.flush();
fos.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
} /**
* @param mainfest文件的路径
* @return String[2]。第一个参数表示 有多少权限。第二个参数则是权限的字符串.第三个参数。是否具有配置文件中的3个权限
*/
public static String[] readPermission(String mainfesttxtPath) { // 读取配置文件的参数
InputStream in;
String pr1 ="";
String pr2 ="";
String pr3 =""; try {
in = new BufferedInputStream(new FileInputStream("e:\\test\\per.properties")); Properties pr = new Properties(); pr.load(in); pr1 = pr.getProperty("pr1").toLowerCase();
pr2 = pr.getProperty("pr2").toLowerCase();
pr3 = pr.getProperty("pr3").toLowerCase();
} catch (FileNotFoundException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
} catch (IOException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
} String[] returnArray = new String[3];
File f = new File(mainfesttxtPath); FileInputStream fis = null;
StringBuffer sb = new StringBuffer(); try {
fis = new FileInputStream(f); int c = 0;
byte[] bys = new byte[1024]; try {
while ((c = fis.read(bys)) != -1) {
// fos.write(bys);
sb.append(new String(bys, 0, c));
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} } catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
fis.close(); } catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} String temp = sb.toString().toLowerCase(); // 判断有多少权限
int count = 0; // 获得最后一次出现的位置
String findStr = "<uses-permission"; int p = temp.indexOf(findStr);
while (-1 != p) {
count++;
// System.out.println("第"+count+"权限");
p = temp.indexOf("<uses-permission", p + findStr.length());
} returnArray[0] = count + ""; // 截取权限的字符串
// 找到第一次的位置。
// 找到最后一次的位置。
// 截取字符串即可
int p1 = temp.indexOf("<uses-permission");
int p2 = temp.lastIndexOf("</uses-permission>"); String perStr = temp.substring(p1, p2); returnArray[1] = perStr + "</uses-permission>"; //判断是否具备制定的3个权限。这里全部转换为小写字母进行比对
String configPerStr = "";
if(temp.indexOf(pr1) > 0){
configPerStr +="[具备"+pr1+"权限]";
}
if(temp.indexOf(pr2) > 0){
configPerStr +="[具备"+pr2+"权限]";
}
if(temp.indexOf(pr3) > 0){
configPerStr +="[具备"+pr3+"权限]";
} returnArray[2] = configPerStr; return returnArray; } /**
* 获得目录下的文件。这里只获取一级。不递归。
*
* @param 目录的路径
* @return 目录下文件的数组.
*/
public static File[] getDirFile(String dirPath) {
// TODO Auto-generated method stub
File f = new File(dirPath); File[] fs = null; if (f.isDirectory()) { fs = f.listFiles();
} return fs; } /**
* apk文件。获取权限数据方法。
*/
public static void apkPer(File af) { // String apk = "e:\\test\\TTXL-FengWang-release-1504271406.apk";
String apk = af.getAbsolutePath();
// String apk ="e:\\test\\AndroidManifest.apk";
String zipTargetPath = "e:\\test\\zips";
String logPath = "e:\\test\\log.txt"; String resultPath = "e:\\test\\result.txt"; //当前的时间
Date d = new Date();
DateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); FileUtils.log(logPath,
"\r\n\r\n\r\n--------------------" + af.getName()
+ "开始--------"+format.format(d)+"-----------------"); // 将apk文件变成zip文件
String zipPath = FileUtils.apkToZip(apk, zipTargetPath, false); FileUtils.log(logPath, "\r\n--->>获得zip文件"); // 取得zip文件路径
// System.out.println(zipPath); // 解压zip文件。 try {
FirstZip.unzip(zipPath, "e:\\test\\unzips");
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} // 解压需要时间。这里需要等待
try {
Thread.sleep(1000 * 3);
} catch (InterruptedException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
} FileUtils.log(logPath, "\r\n--->>完成解压"); // 移动main.xml文件到指定目录下。执行bat
FileUtils.moveTo("e:\\test\\unzips\\AndroidManifest.xml",
"e:\\test\\apktools"); FileUtils.log(logPath, "\r\n--->>移动完成"); // 执行cmd命令.
String cmd = "cmd /c start e:\\test\\apktools\\AXMLPrinter.bat";
Runtime rt = Runtime.getRuntime(); try {
Process p = rt.exec(cmd);
} catch (IOException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
} FileUtils.log(logPath, "\r\n--->>运行bat"); try {
Thread.sleep(1000 * 5);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} // 解析mainfest.txt文件。
// 这里读取txt文件。取出里面的权限字符串。
// 这里可以转成xml。读取里面的节点
// 权限字符串。以<uses-permission 与</uses-permission>之间。
String mainfestPath = "e:\\test\\apktools\\AndroidManifest.txt";
String[] perArray = FileUtils.readPermission(mainfestPath); // 组合下字符串。
String result = "\r\n---------" + af.getName()
+ "---------------------";
result += "\r\n拥有的权限数量为" + perArray[0];
// result += "\r\n具体权限为" + perArray[1];
result +="\r\n制定的权限是否具备:"+perArray[2]; result += "\r\n------------------------------"; FileUtils.log(resultPath, result); FileUtils.log(logPath, "\r\n--->>处理权限"); FileUtils.log(logPath, "\r\n-------------------" + af.getName()
+ "结束-------------------------"); // System.out.println(perArray[0]);
// System.out.println("-------------------------");
// System.out.println(perArray[1]); } }
最后补充。这里的解压缩包,使用了apache的ant.jar。自己去下载下吧。博客园没附件功能。。。。
工程下载地址:http://download.csdn.net/detail/douniwan123654/8645939
批量检查APK是否具有指定的权限。的更多相关文章
- FileProvider N 7.0 升级 安装APK 选择文件 拍照 临时权限 MD
Markdown版本笔记 我的GitHub首页 我的博客 我的微信 我的邮箱 MyAndroidBlogs baiqiantao baiqiantao bqt20094 baiqiantao@sina ...
- c# 检查目录,当指定目录不存在时建立目录
/// <remark> /// 检查目录,当指定目录不存在时建立目录 /// </remark> public static void CheckFolder(string ...
- 使用matlab批量处理图像后在指定文件夹存储
使用matlab批量处理图像后在指定文件夹存储 clear;clc;close all; Files=dir('D:\文件及下载相关\文档\MATLAB\postgraduate\Kodak\*.jp ...
- [Android Tips] 27. 检查 APK 是否可调试
使用 Android SDK 提供的 aapt 检查 APK 文件 $ aapt d badging ${APK_FILE} | grep 'application-debuggable' 检查自身 ...
- [Android Pro] 查看 keystore文件的签名信息 和 检查apk文件中的签名信息
1: 查看 keystore文件的签名信息 keytool -list -v -keystore keystoreName -storepass keystorePassword 2: 检查apk文件 ...
- 在多台手机上批量安装apk
1.手机要打开adb调试 2.该程序可以实现台android手机的多个apk批量安装 1.getSeriaoNum.py模块,该模块获取已连接手机的序列号 import os import threa ...
- linux 批量设置文件夹755 文件644权限
linux 批量设置文件夹755 文件644权限 文件来源 http://www.111cn.net/sys/linux/109724.htm 本文章来为各位介绍一篇关于linux 批量设置文件夹75 ...
- 整理的Unity导出安卓工程利用ANT进行多渠道批量打包APK
Unity导出的安卓工程利用ant进行多渠道循环批量打包 一:设置JAVA环境变量 做android开发的配置这个是基础. win7 下配置java环境变量,下面是链接 http://www.cnbl ...
- 批量移动AD用户到指定OU
原文链接:http://blog.51cto.com/shubao/1346469 作为域管理员,在日常工作中使用ADUC(AD用户和计算机)工具在图形界面中进行账号管理操作可谓是家常便饭了.然而一个 ...
随机推荐
- [转]ubuntu的which、whereis、locate和find命令
which 只能寻找执行文件 ,并在PATH变量里面寻找. whereis 从linux文件数据库(/var/lib/slocate/slocate.db)寻找,所以有可能找到刚刚删除,或者没有发现 ...
- lucene 中关于Store.YES 关于Store.NO的解释
总算搞明白 lucene 中关于Store.YES 关于Store.NO的解释了 一直对Lucene Store.YES不太理解,网上多数的说法是存储字段,NO为不存储. 这样的解释有点郁闷:字面意 ...
- POJ 1236 Network of Schools(tarjan算法 + LCA)
这个题目网上有很多答案,代码也很像,不排除我的.大家的思路应该都是taijan求出割边,然后找两个点的LCA(最近公共祖先),这两个点和LCA以及其他点构成了一个环,我们判断这个环上的割边有几条,我们 ...
- HDU 3861 The King’s Problem(tarjan连通图与二分图最小路径覆盖)
题意:给我们一个图,问我们最少能把这个图分成几部分,使得每部分内的任意两点都能至少保证单向连通. 思路:使用tarjan算法求强连通分量然后进行缩点,形成一个新图,易知新图中的每个点内部的内部点都能保 ...
- Oracle Sql优化之报表和数据仓库运算
1.行转列:有两种写法,一种是case when end写法,另一种写法是pivot(oracle 11g新增) select job, then sal end) as sal10, then sa ...
- android5.0----SVG
SVG ----scalable vector Graphics 可缩放矢量图形 android L 即android 5.0的新特性. 1,SVG是干什么的? 可缩放矢量图形是基于可扩展标记语言(标 ...
- 用DIV+CSS做网页里要设置body和*规定内容
body{}表示是对body标签的设置,就是<html><head></head><body></body></html> 里面 ...
- EXCEL读写NPOI
1.第一步: 可以使用ExcelAutomation进行EXCEl文件的读写,但是需要电脑上安装EXCEL,对EXCEL版本有要求,速度慢,有安全性,并发性问题,不适合网站类项目. 第二种方法: NP ...
- 一段代码详解JavaScript面向对象
(function(){ //私有静态成员 var user = ""; //私有静态方法 function privateStaticMethod(){ } Box = func ...
- ignite学习笔记
1.一个Ignite节点可以从命令行启动,可以用默认的配置也可以传递一个配置文件.可以启动很多很多的节点然后他们会自动地发现对方. 2.Ignite只需要一个ignite-core强依赖,通常你还需要 ...