如何才能拉自己的Android应用程序的(私人)数据?

尝试使用单个文件

adb pull /data/data/com.corp.appName/files/myFile.txt myFile.txt 

失败

 failed to copy '/data/data/com.corp.appName/files/myFile.txt myFile.txt' to 'myFile.txt': Permission denied 

尽pipe设备上启用了USBdebugging。

我们可以通过古老的路线来解决问题

 adb shell run-as com.corp.appName cat files/myFile.txt > myFile.txt 

但是这对于多个文件来说是很笨拙的。

如何将目录/data/data/com.corp.appName/files拉到我的MacBook?

直接或者通过`/ storage / sdcard0 / myDir(从我可以继续使用Android文件传输的地方)的过境来做到这一点都不错。

额外的评论

这可能只是跑步

 adb backup -f myFiles com.corp.appName 

将生成我正在寻找的文件。 在这种情况下,我正在寻找一种方法来解压/解压缩生成的备份!

adb备份将写一个Android特定的档案:

 adb backup -f myAndroidBackup.ab com.corp.appName 

这个档案可以转换成tar格式,使用:

 dd if=myAndroidBackup.ab bs=24 skip=1 | openssl zlib -d > myAndroidBackup.tar 

参考:

http://nelenkov.blogspot.ca/2012/06/unpacking-android-backups.html

在该链接上search“更新”。


或者,使用Android备份提取器从Android备份( .ab )文件中提取文件。

我有同样的问题,但解决它运行以下:

 $ adb shell $ run-as {app-package-name} $ cd /data/data/{app-package-name} $ chmod 777 {file} $ cp {file} /mnt/sdcard/ 

之后你可以运行

 $ adb pull /mnt/sdcard/{file} 

这是什么对我有用:

 adb -d shell "run-as com.example.test cat /data/data/com.example.test/databases/data.db" > data.db 

我正在将数据库直接打印到本地文件中。

在MacOSX上,通过结合来自Calaf和Ollie Ford的答案,以下为我工作。

在命令行(确保adb在你的path中,我的是在〜/ Library / Android / sdk / platform-tools / adb),并且在你的android设备插入并且在USBdebugging模式下运行:

  adb backup -f backup com.mypackage.myapp 

您的Android设备将要求您备份您的数据的权限。 select“备份我的数据”

等一下。

文件备份将出现在您运行adb的目录中。

现在运行:

 dd if=backup bs=1 skip=24 | python -c "import zlib,sys;sys.stdout.write(zlib.decompress(sys.stdin.read()))" > backup.tar 

现在你将拥有一个backup.tar文件,你可以像这样解压:

  tar xvf backup.tar 

并查看您的应用程序存储的所有文件。

你可以在下面使用这个shell脚本。 它也能够从应用程序caching拉取文件,而不像adb backup工具:

 #!/bin/sh if [ -z "$1" ]; then echo "Sorry script requires an argument for the file you want to pull." exit 1 fi adb shell "run-as com.corp.appName cat '/data/data/com.corp.appNamepp/$1' > '/sdcard/$1'" adb pull "/sdcard/$1" adb shell "rm '/sdcard/$1'" 

那么你可以像这样使用它:

 ./pull.sh files/myFile.txt ./pull.sh cache/someCachedData.txt 

这个答案是基于我的经验与其他答案,并在答案的意见。 我的希望是我可以帮助处于类似情况的人。

我正在通过terminal在OSX上执行此操作。

以前Vinicius Avellar的回答对我很好。 我只是大部分时间都需要来自debugging应用程序的设备数据库。

今天我有一个用例,我需要多个私人文件 。 我结束了两个解决scheme,对这种情况有效。

  1. 使用接受的答案以及Someone Somewhere的OSX特定注释。 创build备份并使用第三方解决schemesourceforge.net/projects/adbextractor/files/?source=navbar将其解压缩成 tar。 在这个答案的底部,我将更详细地介绍这个解决scheme的经验。 向下滚动,如果这是你正在寻找。

  2. 我解决了一个更快的解决scheme。 我创build了一个类似于Tamas的答案的拉多个文件的脚本。 我可以这样做,因为我的应用程序是一个debugging应用程序,我有权访问我的设备上运行。 如果您没有权限运行,则在OSX上,此方法不适用于您。

这是我的脚本拉动多个私人文件,我将分享给你,读者,谁也在调查这个真棒问题;):

 #!/bin/bash # # Strict mode: http://redsymbol.net/articles/unofficial-bash-strict-mode/ set -euo pipefail IFS=$'\n\t' # # Usage: script -f fileToPull -p packageName # # This script is for pulling private files from an Android device # using run-as. Note: not all devices have run-as access, and # application must be a debug version for run-as to work. # # If run-as is deactivated on your device use one of the # alternative methods here: # http://stackoverflow.com/questions/15558353/how-can-one-pull-the-private-data-of-ones-own-android-app # # If you have encrypted backup files use: # sourceforge.net/projects/adbextractor/files/?source=navbar # From comments in the accepted answer in the above SO question # # If your files aren't encrypted use the accepted answer # ( see comments and other answers for OSX compatibility ) # # This script is open to expansions to allow selecting # device used. Currently first selected device from # adb shell will be used. #Check we have one connected device adb devices -l | grep -e 'device\b' > /dev/null if [ $? -gt 0 ]; then echo "No device connected to adb." exit 1 fi # Set filename or directory to pull from device # Set package name we will run as while getopts f:p: opt; do case $opt in f) fileToPull=$OPTARG ;; p) packageName=$OPTARG ;; esac done; # Block file arg from being blank if [ -z "$fileToPull" ]; then echo "Please specify file or folder to pull with -f argument" exit 1 fi # Block package name arg from being blank if [ -z "$packageName" ]; then echo "Please specify package name to run as when pulling file" exit 1 fi # Check package exists adb shell pm list packages | grep "$packageName" > /dev/null if [ $? -gt 0 ]; then echo "Package name $packageName does not exist on device" exit 1 fi # Check file exists and has permission with run-as fileCheck=`adb shell "run-as $packageName ls $fileToPull"` if [[ $fileCheck =~ "Permission denied" ]] || [[ $fileCheck =~ "No such file or directory" ]]; then echo "Error: $fileCheck" echo "With file -> $fileToPull" exit 1 fi # Function to pull private file # # param 1 = package name # param 2 = file to pull # param 3 = output file function pull_private_file () { mkdir -p `dirname $3` echo -e "\033[0;35m***" >&2 echo -e "\033[0;36m Coping file $2 -> $3" >&2 echo -e "\033[0;35m***\033[0m" >&2 adb shell "run-as $1 cat $2" > $3 } # Check if a file is a directory # # param 1 = directory to check function is_file_dir() { adb shell "if [ -d \"$1\" ]; then echo TRUE; fi" } # Check if a file is a symbolic link # # param 1 = directory to check function is_file_symlink() { adb shell "if [ -L \"$1\" ]; then echo TRUE; fi" } # recursively pull files from device connected to adb # # param 1 = package name # param 2 = file to pull # param 3 = output file function recurse_pull_private_files() { is_dir=`is_file_dir "$2"` is_symlink=`is_file_symlink "$2"` if [ -n "$is_dir" ]; then files=`adb shell "run-as $1 ls \"$2\""` # Handle the case where directory is a symbolic link if [ -n "$is_symlink" ]; then correctPath=`adb shell "run-as $1 ls -l \"$2\"" | sed 's/.*-> //' | tr -d '\r'` files=`adb shell "run-as $1 ls \"$correctPath\""` fi for i in $files; do # Android adds nasty carriage return that screws with bash vars # This removes it. Otherwise weird behavior happens fileName=`echo "$i" | tr -d '\r'` nextFile="$2/$fileName" nextOutput="$3/$fileName" recurse_pull_private_files "$1" "$nextFile" "$nextOutput" done else pull_private_file "$1" "$2" "$3" fi } recurse_pull_private_files "$packageName" "$fileToPull" "`basename "$fileToPull"`" 

要点: https : //gist.github.com/davethomas11/6c88f92c6221ffe6bc26de7335107dd4


回到方法1 ,使用Android Backup Extractor解密备份

以下是我在Mac上采取的步骤,以及我遇到的问题:

首先我排队备份(并设置密码来encryption我的备份,我的设备需要它):

 adb backup -f myAndroidBackup.ab com.corp.appName 

第二我从这里下载abe.jar: https ://sourceforge.net/projects/adbextractor/files/abe.jar/download

接下来我跑了:

 java -jar ./abe.jar unpack myAndroidBackup.ab myAndroidBackup.tar 

此时我收到一条错误消息。 由于我的档案被encryption,Java给了我一个错误,我需要安装一些安全策略库。

最后我刚跑( 在再次运行上一个命令之后

 tar xvf myAndroidBackup.tar 

现在需要注意的是,如果你可以运行,像猫一样,速度要快得多。 一,你只得到你想要的文件,而不是整个应用程序。 二,更多的文件(encryption对我来说)使传输速度变慢。 所以,如果你没有在OSX上运行,那么知道这样做是很重要的,但是脚本应该首先转到debugging应用程序。

请注意,我今天只是写了一遍,经过几次testing,所以请告诉我任何错误!

通过添加以下代码设置正确的权限后:

 File myFile = ...; myFile.setReadable(true, false); // readable, not only for the owner 

adb pull按需要工作。

请参阅File.setReadable()

从Dave Thomas脚本开始我已经能够写出自己的解决scheme来克服2个问题:

  1. 我的备份只包含清单文件
  2. 与戴夫托马斯得到的二进制文件不可读

这是我的脚本,它将应用程序数据复制到SD卡,然后将其拖动

 #Check we have one connected device adb devices -l | grep -e 'device\b' > /dev/null if [ $? -gt 0 ]; then echo "No device connected to adb." exit 1 fi # Set filename or directory to pull from device # Set package name we will run as while getopts f:p: opt; do case $opt in f) fileToPull=$OPTARG ;; p) packageName=$OPTARG ;; esac done; # Block package name arg from being blank if [ -z "$packageName" ]; then echo "Please specify package name to run as when pulling file" exit 1 fi # Check package exists adb shell pm list packages | grep "$packageName" > /dev/null if [ $? -gt 0 ]; then echo "Package name $packageName does not exist on device" exit 1 fi adb shell "run-as $packageName cp -r /data/data/$packageName/ /sdcard/$packageName" adb pull /sdcard/$packageName adb shell rm -rf /sdcard/$packageName 

与Tamas的答案类似,这里是Mac OS X的your.app.id ,用你的设备从your.app.id获取应用程序的所有文件,并保存到(在这种情况下) ~/Desktop/your.app.id

 ( id=your.app.id && dest=~/Desktop && adb shell "run-as $id cp -r /data/data/$id /sdcard" && adb -d pull "/sdcard/$id" "$dest" && if [ -n "$id" ]; then adb shell "rm -rf /sdcard/$id"; fi ) 
  • 从模拟器中排除-d
  • 不要踩你的会话variables
  • 您可以将整个块粘贴到Terminal.app中(或者如果需要,可以删除换行符)

使用apk备份游戏数据 。 牛轧糖Oneplus 2。

 **adb backup "-apk com.nekki.shadowfight" -f "c:\myapk\samsung2.ab"** 

这是否意味着可以从世界chmod目录:-x到world:rx足够长以便能够获取文件?

对,就是这样。 奇怪的是,你也需要文件来设置x位。 (至less在Android 2.3上)

chmod 755一直向下工作来复制一个文件(但是如果你打算继续使用这个设备,你应该在之后恢复权限)。