Как программно очистить данные приложения

152

Я занимаюсь разработкой автоматизированных тестов для приложений Android (с использованием Robotium). Чтобы обеспечить последовательность и надежность тестов, я хотел бы начинать каждый тест с чистого состояния (тестируемого приложения). Для этого мне нужно очистить данные приложения. Это можно сделать вручную в меню «Настройки» / «Приложения» / «Управление приложениями» / [My App] / «Очистить данные».

Каков рекомендуемый способ сделать это программно?

user597603
источник
Возможно ли использовать инструмент adb для очистки данных между запусками приложений? adb -w
smith324
К сожалению, эта опция недоступна (справка adb устарела).
user597603
Это было бы так здорово. При отладке проблем с базой данных мне приходится так часто переходить к опции «Очистить данные», и это действительно нарушает мой поток.
Джейсон Прадо,
Как это сделать с помощью Android Studio обсуждается здесь: stackoverflow.com/q/31713579/905686 .
user905686
В частности, сделать это: stackoverflow.com/a/57461180/94557
Мэтт Вулф

Ответы:

171

Вы можете использовать инструмент менеджера пакетов для очистки данных для установленных приложений (аналогично нажатию кнопки «очистить данные» в настройках приложения на вашем устройстве). Таким образом, используя ADB, вы можете сделать:

adb shell pm clear my.wonderful.app.package
edovino
источник
1
На Android 2.1-update1 это, к сожалению, дает Error: unknown command 'clear'.
Пол Ламмерцма
@Palani: у меня работает для любой версии выше 2.1-r1 (andoid-7). какие-либо сообщения об ошибках?
эдовино
1
Выше команда подключается к оболочке Android и выполняет «pm clear my.wonderful.app.package» в Android. В моем устройстве команда «pm» не имеет опции «clear». Это ничего не связано с SDK. Это зависит от прошивки устройства.
Палани
ищу программные данные из браузера (по умолчанию) и приложений браузера Chrome на устройстве Android из моего приложения для Android. Пожалуйста, помогите мне с этим ..
Бриеш Патель
Не работает на всех устройствах, но это замечательно для устройств, на которых оно работает
Кори Трезе
34

После ответа @ edovino, способ очистки всех настройки приложения.

private void clearPreferences() {
    try {
        // clearing app data
        Runtime runtime = Runtime.getRuntime();
        runtime.exec("pm clear YOUR_APP_PACKAGE_GOES HERE");

    } catch (Exception e) {
        e.printStackTrace();
    }
}

Предупреждение : приложение принудительно закроется.

Себастьяно
источник
5
Если после этого выполняется какой-либо тестовый код, он завершается ошибкой.
Раджат
Требуется ли выполнение этого и какие разрешения должны быть объявлены в манифесте?
Reubenjohn
1
Нет, для этого не требуется никакого специального разрешения.
Себастьяно
Спасибо, ты спас мне жизнь!
Сид
1
если я не хочу принудительно закрывать приложение?
NJ
14

Из API версии 19 можно вызывать ActivityManager.clearApplicationUserData ().

((ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE)).clearApplicationUserData();
Йоаким
источник
13
Просто к вашему сведению, вызов этого приведет к прекращению вашего приложения.
Зак Ратнер
8

Проверьте этот код, чтобы:

@Override
protected void onDestroy() {
// closing Entire Application
    android.os.Process.killProcess(android.os.Process.myPid());
    Editor editor = getSharedPreferences("clear_cache", Context.MODE_PRIVATE).edit();
    editor.clear();
    editor.commit();
    trimCache(this);
    super.onDestroy();
}


public static void trimCache(Context context) {
    try {
        File dir = context.getCacheDir();
        if (dir != null && dir.isDirectory()) {
            deleteDir(dir);

        }
    } catch (Exception e) {
        // TODO: handle exception
    }
}


public static boolean deleteDir(File dir) {
    if (dir != null && dir.isDirectory()) {
        String[] children = dir.list();
        for (int i = 0; i < children.length; i++) {
            boolean success = deleteDir(new File(dir, children[i]));
            if (!success) {
                return false;
            }
        }
    }

    // <uses-permission
    // android:name="android.permission.CLEAR_APP_CACHE"></uses-permission>
    // The directory is now empty so delete it

    return dir.delete();
}
Харе Кришна
источник
6

Если у вас есть только пара общих настроек для очистки, то это решение гораздо приятнее .

@Override
protected void setUp() throws Exception {
    super.setUp();
    Instrumentation instrumentation = getInstrumentation();
    SharedPreferences preferences = instrumentation.getTargetContext().getSharedPreferences(...), Context.MODE_PRIVATE);
    preferences.edit().clear().commit();
    solo = new Solo(instrumentation, getActivity());
}
Томас Келлер
источник
Разве это не требует включения «режима инструментовки» ? Что это за режим?
ADTC
Да, для этого требуется «инструментальное» приложение, т. Е. Ваш тест выполняется вместе с кодом приложения на реальном обрабатываемом устройстве , что означает, что вы можете получить доступ ко всему состоянию вашего приложения и изменить его во время выполнения для целей тестирования.
Томас Келлер
что должно быть в (...)?
NickUnuchek
@NickUnuchek Имя файла настроек.
Томас Келлер
3

Используя Context , мы можем очистить определенные файлы приложения, такие как настройки, файл базы данных. Я использовал приведенный ниже код для тестирования пользовательского интерфейса с помощью Espresso.

    @Rule
    public ActivityTestRule<HomeActivity> mActivityRule = new ActivityTestRule<>(
            HomeActivity.class);

    public static void clearAppInfo() {
        Activity mActivity = testRule.getActivity();
        SharedPreferences prefs =
                PreferenceManager.getDefaultSharedPreferences(mActivity);
        prefs.edit().clear().commit();
        mActivity.deleteDatabase("app_db_name.db");
    }
Ронак Пория
источник
3

Самый простой способ сделать это

private void deleteAppData() {
         try {
        // clearing app data
        String packageName = getApplicationContext().getPackageName();
        Runtime runtime = Runtime.getRuntime();
        runtime.exec("pm clear "+packageName);

    } catch (Exception e) {
        e.printStackTrace();
    } 
}

Это очистит данные и удалит ваше приложение из памяти. Это эквивалентно опции очистки данных в разделе «Настройки» -> «Менеджер приложений» -> «Ваше приложение» -> «Очистить данные».

Это полностью удалит данные и принудительно закроет приложение.

Summved Jain
источник
Пожалуйста, не добавляйте один и тот же ответ на несколько вопросов. Ответьте лучшим и отметьте остальные как дубликаты. См. Допустимо ли добавить дублирующий ответ на несколько вопросов?
FelixSFD
1
Как мы можем достичь этого без закрытия приложения
Омкар Гурье
2

Это решение действительно помогло мне:

Используя два следующих метода, мы можем очистить данные программно

    public void clearApplicationData() {
    File cacheDirectory = getCacheDir();
    File applicationDirectory = new File(cacheDirectory.getParent());
    if (applicationDirectory.exists()) {
    String[] fileNames = applicationDirectory.list();
        for (String fileName : fileNames) {
            if (!fileName.equals("lib")) {
                deleteFile(new File(applicationDirectory, fileName));
            }
        }
    }
}
    public static boolean deleteFile(File file) {
    boolean deletedAll = true;
    if (file != null) {
        if (file.isDirectory()) {
            String[] children = file.list();
            for (int i = 0; i < children.length; i++) {
                deletedAll = deleteFile(new File(file, children[i])) && deletedAll;
            }
        } else {
            deletedAll = file.delete();
        }
    }

    return deletedAll;
}
Приянка С.Н.
источник
2

Если версия Android выше Kitkat, вы можете использовать это

public void onClick (Просмотреть представление) {

    Context context = getApplicationContext(); // add this line
    if (Build.VERSION_CODES.KITKAT <= Build.VERSION.SDK_INT) {
        ((ActivityManager) context.getSystemService(ACTIVITY_SERVICE))
            .clearApplicationUserData();
        return;
    }
Тушар Саха
источник
0

Каков рекомендуемый способ сделать это программно?

Единственный возможный вариант - запустить команду ADB adb shell pm clear packageперед тестом. Самая большая проблема в том, что это своего рода головная боль, сочетающая выполнение тестов и команды оболочки.

Тем не менее, мы (в Mediafe) пришли с некоторым решением, которое может работать для вас на обычном устройстве без рута. Все, что вам нужно сделать, это добавить аннотацию. Все остальное делается с помощью простого скрипта bash .

Просто добавь @ClearData аннотацию до ЛЮБОГО из ваших тестов и tada command, команда ADB clear будет выполнена перед выполнением теста.

Вот пример такого теста:

@Test
@ClearData
public void someTest() {
    // your test
}

Идея заключается в следующем

  1. Прочитайте все тесты, используя adb shell am instrument -e log true
  2. Создайте план выполнения, анализируя выходные данные из (1)
  3. Выполнить план выполнения построчно

Используя ту же идею, все эти опции вы можете легко поддержать:

  • Очистить данные
  • Очистить панель уведомлений
  • Параметрирование
  • Фильтровать и запускать по тегам

Используйте только аннотации. Как это:

@Test
@ClearData
@Tags(tags = {"sanity", "medium"})
@Parameterized.Repeat(count = 3)
public void myTest() throws Exception {
    String param = params[index];
    // ...
}

Бонус! 🎁 Для каждого неудачного теста:

  • Собрать Logcat + Stacktrace
  • Запись видео (mp4)
  • Дамп БД (sqlite)
  • Дамп общих настроек по умолчанию (xml)
  • Соберите файлы dumpsys, такие как: батарея, netstats и другие.

В общем, легко добавить больше опций, поскольку тесты выполняются один за другим из скрипта bash, а не из задачи gradle.

Post Полный пост в блоге : https://medium.com/medisafe-tech-blog/running-android-ui-tests-53e85e5c8da8

📘 Исходный код с примерами : https://github.com/medisafe/run-android-tests

Надеюсь, что это отвечает на вопрос 6 лет;)

sromku
источник