package com.cheng.utils;
import android.app.ActivityManager;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.Signature;
import android.net.Uri;
import android.text.TextUtils;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.math.BigInteger;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.security.PublicKey;
import java.security.cert.CertificateException;
import java.security.cert.CertificateFactory;
import java.security.cert.X509Certificate;
import java.util.List;
import javax.security.auth.x500.X500Principal;
/**
* App工具类
*/
public class AppUtil {
private final static X500Principal DEBUG_DN = new X500Principal(
"CN=Android Debug,O=Android,C=US");
static {
Logger.TAG = "AppUtil";
}
private AppUtil() {
throw new Error("Do not need instantiate!");
}
/**
* 得到软件版本号
* @param context 上下文
* @return 当前版本Code
*/
public static int getVerCode(Context context) {
if (context == null) return 1;
int verCode = -1;
try {
String packageName = context.getPackageName();
verCode = context.getPackageManager().getPackageInfo(packageName, 0).versionCode;
} catch (PackageManager.NameNotFoundException e) {
Logger.e(e);
}
return verCode;
}
/**
* 获取应用运行的最大内存
* @return 最大内存
*/
public static long getMaxMemory() {
return Runtime.getRuntime().maxMemory() / 1024;
}
/**
* 得到软件显示版本信息
* @param context 上下文
* @return 当前版本信息
*/
public static String getVerName(Context context) {
if (context == null) return "";
String verName = "";
try {
String packageName = context.getPackageName();
verName = context.getPackageManager().getPackageInfo(packageName, 0).versionName;
} catch (PackageManager.NameNotFoundException e) {
Logger.e(e);
}
return verName;
}
/**
* 安装apk
* @param context 上下文
* @param file APK文件
*/
public static void installApk(Context context, File file) {
if (context == null) return;
if (file == null) return;
Intent intent = new Intent();
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setAction(Intent.ACTION_VIEW);
intent.setDataAndType(Uri.fromFile(file),
"application/vnd.android.package-archive");
context.startActivity(intent);
}
/**
* 安装apk
* @param context 上下文
* @param file APK文件uri
*/
public static void installApk(Context context, Uri file) {
if (context == null) return;
if (file == null) return;
Intent intent = new Intent();
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
intent.setAction(Intent.ACTION_VIEW);
intent.setDataAndType(file, "application/vnd.android.package-archive");
context.startActivity(intent);
}
/**
* 卸载apk
* @param context 上下文
* @param packageName 包名
*/
public static void uninstallApk(Context context, String packageName) {
if (context == null) return;
if (TextUtils.isEmpty(packageName)) return;
Intent intent = new Intent(Intent.ACTION_DELETE);
Uri packageURI = Uri.parse("package:" + packageName);
intent.setData(packageURI);
context.startActivity(intent);
}
/**
* 检测服务是否运行
* @param context 上下文
* @param className 类名
* @return 是否运行的状态
*/
public static boolean isServiceRunning(Context context, String className) {
if (context == null) return false;
if (TextUtils.isEmpty(className)) return false;
boolean isRunning = false;
ActivityManager activityManager = (ActivityManager) context
.getSystemService(Context.ACTIVITY_SERVICE);
List<ActivityManager.RunningServiceInfo> servicesList = activityManager
.getRunningServices(Integer.MAX_VALUE);
for (ActivityManager.RunningServiceInfo si : servicesList) {
if (className.equals(si.service.getClassName())) {
isRunning = true;
}
}
return isRunning;
}
/**
* 停止运行服务
* @param context 上下文
* @param className 类名
* @return 是否执行成功
*/
public static boolean stopRunningService(Context context, String className) {
if (context == null) return false;
if (TextUtils.isEmpty(className)) return false;
Intent intentService = null;
boolean ret = false;
try {
intentService = new Intent(context, Class.forName(className));
} catch (Exception e) {
Logger.e(e);
}
if (intentService != null) {
// TODO 此处的context需要为Activity?
ret = context.stopService(intentService);
}
return ret;
}
/**
* whether this process is named with processName
* @param context 上下文
* @param processName 进程名
* @return <ul>
* return whether this process is named with processName
* <li>if context is null, return false</li>
* <li>if {@link ActivityManager#getRunningAppProcesses()} is null,
* return false</li>
* <li>if one process of
* {@link ActivityManager#getRunningAppProcesses()} is equal to
* processName, return true, otherwise return false</li>
* </ul>
*/
public static boolean isNamedProcess(Context context, String processName) {
if (context == null || TextUtils.isEmpty(processName)) {
return false;
}
int pid = android.os.Process.myPid();
ActivityManager manager = (ActivityManager) context
.getSystemService(Context.ACTIVITY_SERVICE);
List<ActivityManager.RunningAppProcessInfo> processInfoList = manager
.getRunningAppProcesses();
if (processInfoList == null) {
return true;
}
for (ActivityManager.RunningAppProcessInfo processInfo : manager
.getRunningAppProcesses()) {
if (processInfo.pid == pid
&& processName.equalsIgnoreCase(processInfo.processName)) {
return true;
}
}
return false;
}
/**
* whether application is in background
* <ul>
* <li>need use permission android.permission.GET_TASKS in Manifest.xml</li>
* </ul>
* @param context 上下文
* @return if application is in background return true, otherwise return
* false
*/
public static boolean isApplicationInBackground(Context context) {
ActivityManager am = (ActivityManager) context
.getSystemService(Context.ACTIVITY_SERVICE);
List<ActivityManager.RunningTaskInfo> taskList = am.getRunningTasks(1);
if (taskList != null && !taskList.isEmpty()) {
ComponentName topActivity = taskList.get(0).topActivity;
if (topActivity != null
&& !topActivity.getPackageName().equals(
context.getPackageName())) {
return true;
}
}
return false;
}
/**
* 获取应用的签名信息
* @param context
* @return
*/
static public String getSingInfo(Context context) {
StringBuilder sb = new StringBuilder();
Signature signature = getApkSignature(context);
if (signature == null) return "";
ByteArrayInputStream bais = new ByteArrayInputStream(signature.toByteArray());
try {
CertificateFactory certificateFactory = CertificateFactory.getInstance("X.509");
X509Certificate certificate = (X509Certificate) certificateFactory.generateCertificate(bais);
String version = String.valueOf(certificate.getVersion());
String serialNumber = certificate.getSerialNumber().toString(16);
String subjectDN = certificate.getSubjectDN().toString();
String issuerDN = certificate.getIssuerDN().toString();
String notBefore = certificate.getNotBefore().toString();
String notAfter = certificate.getNotAfter().toString();
String sigAlgName = certificate.getSigAlgName();
byte[] sig = certificate.getSignature();
String signatureStr = new BigInteger(sig).toString(16);
PublicKey publicKey = certificate.getPublicKey();
byte[] pkenc = publicKey.getEncoded();
StringBuilder pkencSB = new StringBuilder();
for (int i=0; i<pkenc.length; i++) {
pkencSB.append(i+",");
}
sb.append(version);
sb.append(serialNumber);
sb.append(serialNumber);
sb.append(subjectDN);
sb.append(issuerDN);
sb.append(notBefore);
sb.append(notAfter);
sb.append(sigAlgName);
sb.append(signatureStr);
sb.append(pkencSB);
Logger.e("版本号 " + version);
Logger.e("序列号 " + serialNumber);
Logger.e("全名 " + subjectDN);
Logger.e("签发者全名n" + issuerDN);
Logger.e("有效期起始日 " + notBefore);
Logger.e("有效期截至日 " + notAfter);
Logger.e("签名算法 " + sigAlgName);
Logger.e("签名n " + signatureStr);
Logger.e("公钥 " + pkencSB.toString());
Logger.e("SingInfo " + sb.toString());
} catch (CertificateException e) {
Logger.e(e);
}
return sb.toString();
}
static public String getApkMD5(Context context) {
String apkMD5 = "";
Signature signature = getApkSignature(context);
if (signature == null) return apkMD5;
MessageDigest messageDigest = null;
try {
messageDigest = MessageDigest.getInstance("MD5");
} catch (NoSuchAlgorithmException e) {
Logger.e(e);
}
messageDigest.update(signature.toByteArray());
byte[] digest = messageDigest.digest();
apkMD5 = toHexString(digest);
Logger.e("Apk MD5 : "+apkMD5);
return apkMD5;
}
static public String getApkSHA1(Context context) {
String apkSHA1 = "";
Signature signature = getApkSignature(context);
if (signature == null) return apkSHA1;
MessageDigest messageDigest = null;
try {
messageDigest = MessageDigest.getInstance("SHA1");
} catch (NoSuchAlgorithmException e) {
Logger.e(e);
}
messageDigest.update(signature.toByteArray());
byte[] digest = messageDigest.digest();
apkSHA1 = toHexString(digest);
Logger.e("Apk SHA1 : " + apkSHA1);
return apkSHA1;
}
/**
* 检测当前应用是否是Debug版本
*
* @param ctx
* @return
*/
public static boolean isDebuggable(Context ctx) {
boolean debuggable = false;
try {
PackageInfo pinfo = ctx.getPackageManager().getPackageInfo(ctx.getPackageName(), PackageManager.GET_SIGNATURES);
Signature signatures[] = pinfo.signatures;
for (int i = 0; i < signatures.length; i++) {
CertificateFactory cf = CertificateFactory.getInstance("X.509");
ByteArrayInputStream stream = new ByteArrayInputStream(signatures[i].toByteArray());
X509Certificate cert = (X509Certificate) cf
.generateCertificate(stream);
debuggable = cert.getSubjectX500Principal().equals(DEBUG_DN);
if (debuggable)
break;
}
} catch (PackageManager.NameNotFoundException e) {
Logger.e(e);
return false;
} catch (CertificateException e) {
Logger.e(e);
return false;
}
return debuggable;
}
static private Signature getApkSignature(Context context) {
PackageInfo packageInfo = null;
Signature signature = null;
try {
packageInfo = context.
getPackageManager().
getPackageInfo(
context.getPackageName(),
PackageManager.GET_SIGNATURES);
signature = packageInfo.signatures[0];
} catch (PackageManager.NameNotFoundException e) {
Logger.e(e);
}
return signature;
}
static private void byte2hex(byte b, StringBuffer buf) {
char[] hexChars = { '0', '1', '2', '3', '4', '5', '6', '7', '8',
'9', 'A', 'B', 'C', 'D', 'E', 'F' };
int high = ((b & 0xf0) >> 4);
int low = (b & 0x0f);
buf.append(hexChars[high]);
buf.append(hexChars[low]);
}
static private String toHexString(byte[] block) {
StringBuffer buf = new StringBuffer();
int len = block.length;
for (int i = 0; i < len; i++) {
byte2hex(block[i], buf);
if (i < len - 1) {
buf.append(":");
}
}
return buf.toString();
}
}