用例就是这样。我为公司编写自定义应用程序。这些应用程序是专有的,由于各种原因不适合Android Market。有些客户要求应用程序定期自动联系公司服务器以检查更新,并在需要时自动下载并安装它们。我有一个工作机制来做到这一点,但它没有我想要的那么强大。最好的解决方案是在设备上运行的应用程序,将其Android versionCode(可能还有VersionName)传递给服务器,在服务器上将这些与服务器上潜在升级.apk的versionCode进行比较。只有当服务器上的.apk表示升级时,才会将其上传到设备并进行安装。
发布了许多建议的解决方案。一种常见的方法是在服务器上放置一个单独的文本文件,其中包含versionCode和versionName,但是该文本文件的管理错误可能与.apk文件中的值不同步。结果将是持续且不必要的下载。各种其他解决方案,例如使用apktool或其任何包装器,虽然可行,但还有其他缺点。
我正在寻找的解决方法,但似乎都涉及持久保存有关最近下载和安装的.apk文件(例如校验和)的一些其他信息。此信息可以传递给服务器并进行比较。这可以使用,它不是我想要的干净。
我正在寻找一个库.jar文件,它允许从.apk文件中获取versionCode和versionName。基本上是传递表示.apk文件位置的File对象,并提供获取versionCode和versionName的方法。
欢迎提出其他建议。
答案 0 :(得分:0)
我找到了一种方法来做到这一点,但不适合胆小的人。我下载了AXMLPrinter2.jar这是一个自包含的.jar文件,可用于读取,解释和显示android .XML文件的内容。特别是,它以人类可读的格式显示AndroidManifest.xml的内容做得很好。但是,我需要以编程方式访问AndroidManifest.xml的内容。
这是有趣的地方。
我首先在AXMLPrinter2.jar中提取了MANIFEST.XML文件,以找到主类,即AXMLPrinter。
然后我对AXMLPrinter.class进行了反编译,结果证明它是围绕AXMLPrinter2.jar中包含的AXML解析器的一个相对简单的包装器,并派生了一个名为ReadAndroidManifest的新类。由于这个类是在服务器上使用的,它有一个简单的构造函数ReadAndroidManifest(File apkFile)并提供了两个方法:getVersionCode()和getVersionName()。
我只是将AXMLPrinter2.jar文件添加到我的web-app库(未修改!),并在servlet的一部分中包含派生类ReadAndroidManifest,该类确定apk文件是否代表升级。
显然,这种技术可以通过更通用的方式扩展,以提供对AndroidManifest.xml文件的所有元素的访问,但上面的简单版本可以完美地用于我的目的。
答案 1 :(得分:0)
我正在努力做同样的事情,在阅读了这么多帖子之后,我进入了一种解决方法,我认为这是通过纯JAVA代码从Android中获取packageName和版本的最舒适方式(在Android之外)环境)。
首先,我已经下载了apktool。如果链接由于某种原因不起作用,它是apktool,下载页面下的名称为 apktool依赖项和windows 的帮助程序脚本。然后,我解压缩文件夹并获取其aapt.exe,放入我的java项目文件夹。
然后,在我的Java代码中,我只是这样写:
ProcessBuilder builder = new ProcessBuilder("PATH_TO_APKTOOL_AAPT.exe", "dump", "badging", "path_to_your_apk_file");
Process p;
String output = "";
try {
p = builder.start();
BufferedReader r = new BufferedReader(new InputStreamReader(p.getInputStream()));
String line;
while (true) {
line = r.readLine();
if (line == null) { break; }
output += line;
}
Pattern pattern = Pattern.compile("package: name='(.*?)'", Pattern.CASE_INSENSITIVE);
Matcher m = pattern.matcher(output);
m.find();
System.out.println("package name:" + m.group(1).trim());
pattern = Pattern.compile("package:.*?versionCode='(.*?)'", Pattern.CASE_INSENSITIVE);
m = pattern.matcher(output);
m.find();
System.out.println("version:" + m.group(1).trim());
} catch (IOException e) {
e.printStackTrace();
}
`
嗯,这是一种较少的副作用和获取APK包名称和版本代码的简单方法:)