diff --git a/app/src/main/java/app/fedilab/android/activities/BaseMainActivity.java b/app/src/main/java/app/fedilab/android/activities/BaseMainActivity.java index 1d6cc9dd9..c1c6131d4 100644 --- a/app/src/main/java/app/fedilab/android/activities/BaseMainActivity.java +++ b/app/src/main/java/app/fedilab/android/activities/BaseMainActivity.java @@ -1049,12 +1049,10 @@ public abstract class BaseMainActivity extends BaseActivity ActivityCompat.requestPermissions(BaseMainActivity.this, new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, Helper.EXTERNAL_STORAGE_REQUEST_CODE); } else { Intent backupIntent = new Intent(BaseMainActivity.this, BackupStatusService.class); - backupIntent.putExtra("userId", userId); startService(backupIntent); } }else{ Intent backupIntent = new Intent(BaseMainActivity.this, BackupStatusService.class); - backupIntent.putExtra("userId", userId); startService(backupIntent); } return true; diff --git a/app/src/main/java/app/fedilab/android/activities/MainApplication.java b/app/src/main/java/app/fedilab/android/activities/MainApplication.java index 096901281..3d84a697c 100644 --- a/app/src/main/java/app/fedilab/android/activities/MainApplication.java +++ b/app/src/main/java/app/fedilab/android/activities/MainApplication.java @@ -41,6 +41,7 @@ import java.util.Locale; import app.fedilab.android.helper.Helper; import app.fedilab.android.jobs.ApplicationJob; +import app.fedilab.android.jobs.BackupStatusesSyncJob; import app.fedilab.android.jobs.NotificationsSyncJob; import es.dmoral.toasty.Toasty; import app.fedilab.android.BuildConfig; @@ -68,6 +69,7 @@ public class MainApplication extends MultiDexApplication { //System.setProperty("java.net.preferIPv4Stack" , "true"); JobManager.create(this).addJobCreator(new ApplicationJob()); NotificationsSyncJob.schedule(false); + BackupStatusesSyncJob.schedule(false); StrictMode.VmPolicy.Builder builder = new StrictMode.VmPolicy.Builder(); StrictMode.setVmPolicy(builder.build()); SharedPreferences sharedpreferences = getSharedPreferences(Helper.APP_PREFS, android.content.Context.MODE_PRIVATE); diff --git a/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java b/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java index d5414647f..5229bdf41 100644 --- a/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java +++ b/app/src/main/java/app/fedilab/android/fragments/ContentSettingsFragment.java @@ -297,6 +297,20 @@ public class ContentSettingsFragment extends Fragment implements ScreenShotable count4 = 0; count5 = 0; + String userId = sharedpreferences.getString(Helper.PREF_KEY_ID, null); + String instance = sharedpreferences.getString(Helper.PREF_INSTANCE, Helper.getLiveInstance(context)); + + boolean auto_backup = sharedpreferences.getBoolean(Helper.SET_AUTO_BACKUP_STATUSES+userId+instance, false); + final CheckBox set_auto_backup = rootView.findViewById(R.id.set_auto_backup); + set_auto_backup.setChecked(auto_backup); + set_auto_backup.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View v) { + SharedPreferences.Editor editor = sharedpreferences.edit(); + editor.putBoolean(Helper.SET_AUTO_BACKUP_STATUSES+userId+instance, set_auto_backup.isChecked()); + editor.apply(); + } + }); TagsEditText set_featured_tags = rootView.findViewById(R.id.set_featured_tags); @@ -447,8 +461,6 @@ public class ContentSettingsFragment extends Fragment implements ScreenShotable } }); - String userId = sharedpreferences.getString(Helper.PREF_KEY_ID, null); - String instance = sharedpreferences.getString(Helper.PREF_INSTANCE, Helper.getLiveInstance(context)); boolean display_admin_menu = sharedpreferences.getBoolean(Helper.SET_DISPLAY_ADMIN_MENU + userId + instance, false); diff --git a/app/src/main/java/app/fedilab/android/helper/Helper.java b/app/src/main/java/app/fedilab/android/helper/Helper.java index 488fc86c9..6be557005 100644 --- a/app/src/main/java/app/fedilab/android/helper/Helper.java +++ b/app/src/main/java/app/fedilab/android/helper/Helper.java @@ -380,6 +380,7 @@ public class Helper { public static final String SET_DISPLAY_ADMIN_MENU = "set_display_admin_menu"; public static final String SET_DISPLAY_ADMIN_STATUSES = "set_display_admin_statuses"; public static final String SET_DISPLAY_FEDILAB_FEATURES_BUTTON = "set_display_fedilab_features_button"; + public static final String SET_AUTO_BACKUP_STATUSES = "set_auto_backup_statuses"; public static final int S_NO = 0; static final int S_512KO = 1; @@ -472,6 +473,7 @@ public class Helper { public static final String SET_PROXY_PASSWORD = "set_proxy_password"; //Refresh job public static final int MINUTES_BETWEEN_NOTIFICATIONS_REFRESH = 15; + public static final int MINUTES_BETWEEN_BACKUP = 60; public static final int MINUTES_BETWEEN_HOME_TIMELINE = 30; public static final int SPLIT_TOOT_SIZE = 500; diff --git a/app/src/main/java/app/fedilab/android/jobs/ApplicationJob.java b/app/src/main/java/app/fedilab/android/jobs/ApplicationJob.java index af8b1e596..63e373f74 100644 --- a/app/src/main/java/app/fedilab/android/jobs/ApplicationJob.java +++ b/app/src/main/java/app/fedilab/android/jobs/ApplicationJob.java @@ -34,6 +34,8 @@ public class ApplicationJob implements JobCreator { return new ScheduledTootsSyncJob(); case ScheduledBoostsSyncJob.SCHEDULED_BOOST: return new ScheduledBoostsSyncJob(); + case BackupStatusesSyncJob.BACKUP_SYNC: + return new BackupStatusesSyncJob(); default: return null; } diff --git a/app/src/main/java/app/fedilab/android/jobs/BackupStatusesSyncJob.java b/app/src/main/java/app/fedilab/android/jobs/BackupStatusesSyncJob.java new file mode 100644 index 000000000..1ddd400f5 --- /dev/null +++ b/app/src/main/java/app/fedilab/android/jobs/BackupStatusesSyncJob.java @@ -0,0 +1,131 @@ +package app.fedilab.android.jobs; +/* Copyright 2019 Thomas Schneider + * + * This file is a part of Fedilab + * + * This program is free software; you can redistribute it and/or modify it under the terms of the + * GNU General Public License as published by the Free Software Foundation; either version 3 of the + * License, or (at your option) any later version. + * + * Fedilab is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even + * the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General + * Public License for more details. + * + * You should have received a copy of the GNU General Public License along with Fedilab; if not, + * see . */ + +import android.content.Context; +import android.content.Intent; +import android.content.SharedPreferences; +import android.database.sqlite.SQLiteDatabase; +import android.graphics.Bitmap; +import android.graphics.BitmapFactory; +import android.os.Handler; +import android.os.Looper; + +import androidx.annotation.NonNull; +import androidx.annotation.Nullable; + +import com.bumptech.glide.Glide; +import com.bumptech.glide.load.DataSource; +import com.bumptech.glide.load.engine.GlideException; +import com.bumptech.glide.request.RequestListener; +import com.bumptech.glide.request.target.SimpleTarget; +import com.bumptech.glide.request.target.Target; +import com.bumptech.glide.request.transition.Transition; +import com.evernote.android.job.Job; +import com.evernote.android.job.JobManager; +import com.evernote.android.job.JobRequest; + +import java.util.ArrayList; +import java.util.List; +import java.util.Set; +import java.util.concurrent.TimeUnit; + +import app.fedilab.android.R; +import app.fedilab.android.activities.BaseMainActivity; +import app.fedilab.android.activities.MainActivity; +import app.fedilab.android.activities.OwnerStatusActivity; +import app.fedilab.android.client.API; +import app.fedilab.android.client.APIResponse; +import app.fedilab.android.client.Entities.Account; +import app.fedilab.android.client.Entities.Notification; +import app.fedilab.android.fragments.DisplayNotificationsFragment; +import app.fedilab.android.helper.Helper; +import app.fedilab.android.services.BackupStatusInDataBaseService; +import app.fedilab.android.services.BackupStatusService; +import app.fedilab.android.sqlite.AccountDAO; +import app.fedilab.android.sqlite.Sqlite; + +import static app.fedilab.android.helper.Helper.INTENT_ACTION; +import static app.fedilab.android.helper.Helper.INTENT_TARGETED_ACCOUNT; +import static app.fedilab.android.helper.Helper.NOTIFICATION_INTENT; +import static app.fedilab.android.helper.Helper.PREF_INSTANCE; +import static app.fedilab.android.helper.Helper.PREF_KEY_ID; +import static app.fedilab.android.helper.Helper.canNotify; +import static app.fedilab.android.helper.Helper.notify_user; + + +/** + * Created by Thomas on 06/01/2019. + * backup statuses + */ + +public class BackupStatusesSyncJob extends Job { + + static final String BACKUP_SYNC = "job_backup"; + static { + Helper.installProvider(); + } + + @NonNull + @Override + protected Result onRunJob(@NonNull Params params) { + //Code refresh here + + backupService(); + return Result.SUCCESS; + } + + + public static int schedule(boolean updateCurrent) { + + Set jobRequests = JobManager.instance().getAllJobRequestsForTag(BACKUP_SYNC); + if (!jobRequests.isEmpty() && !updateCurrent) { + return jobRequests.iterator().next().getJobId(); + } + + int jobRequestschedule = -1; + try { + jobRequestschedule = new JobRequest.Builder(BackupStatusesSyncJob.BACKUP_SYNC) + .setPeriodic(TimeUnit.MINUTES.toMillis(Helper.MINUTES_BETWEEN_BACKUP), TimeUnit.MINUTES.toMillis(5)) + .setUpdateCurrent(updateCurrent) + .setRequiredNetworkType(JobRequest.NetworkType.METERED) + .setRequirementsEnforced(false) + .build() + .schedule(); + }catch (Exception ignored){} + + return jobRequestschedule; + } + + + /** + * Task in background starts here. + */ + private void backupService() { + SQLiteDatabase db = Sqlite.getInstance(getContext(), Sqlite.DB_NAME, null, Sqlite.DB_VERSION).open(); + final List accounts = new AccountDAO(getContext(), db).getAllAccount(); + SharedPreferences sharedpreferences = getContext().getSharedPreferences(Helper.APP_PREFS, android.content.Context.MODE_PRIVATE); + for(Account account: accounts) { + boolean autobackup = sharedpreferences.getBoolean(Helper.SET_AUTO_BACKUP_STATUSES + account.getId() + account.getInstance(), false); + if( autobackup) { + Intent backupIntent = new Intent(getContext(), BackupStatusInDataBaseService.class); + backupIntent.putExtra("userId", account.getId()); + backupIntent.putExtra("instance", account.getInstance()); + getContext().startService(backupIntent); + } + } + } + +} \ No newline at end of file diff --git a/app/src/main/java/app/fedilab/android/services/BackupStatusInDataBaseService.java b/app/src/main/java/app/fedilab/android/services/BackupStatusInDataBaseService.java index 83eb6b6ec..ab96d9bf9 100644 --- a/app/src/main/java/app/fedilab/android/services/BackupStatusInDataBaseService.java +++ b/app/src/main/java/app/fedilab/android/services/BackupStatusInDataBaseService.java @@ -74,27 +74,42 @@ public class BackupStatusInDataBaseService extends IntentService { @Override protected void onHandleIntent(@Nullable Intent intent) { + boolean toastMessage = true; + String userId = null; + String instance = null; + if( intent != null){ + userId = intent.getStringExtra("userId"); + instance = intent.getStringExtra("instance"); + toastMessage = false; + } + SharedPreferences sharedpreferences = getSharedPreferences(Helper.APP_PREFS, Context.MODE_PRIVATE); + if( userId == null || instance == null) { + userId = sharedpreferences.getString(Helper.PREF_KEY_ID, null); + instance = sharedpreferences.getString(Helper.PREF_INSTANCE, null); + } + boolean finalToastMessage = toastMessage; if( instanceRunning == 0 ){ new Handler(Looper.getMainLooper()).post(new Runnable() { @Override public void run() { - Toasty.info(getApplicationContext(), getString(R.string.data_export_start), Toast.LENGTH_LONG).show(); + if(finalToastMessage) { + Toasty.info(getApplicationContext(), getString(R.string.data_export_start), Toast.LENGTH_LONG).show(); + } } }); }else { new Handler(Looper.getMainLooper()).post(new Runnable() { @Override public void run() { - Toasty.info(getApplicationContext(), getString(R.string.data_export_running), Toast.LENGTH_LONG).show(); + if(finalToastMessage) { + Toasty.info(getApplicationContext(), getString(R.string.data_export_running), Toast.LENGTH_LONG).show(); + } } }); return; } instanceRunning++; String message; - SharedPreferences sharedpreferences = getSharedPreferences(Helper.APP_PREFS, Context.MODE_PRIVATE); - String userId = sharedpreferences.getString(Helper.PREF_KEY_ID, null); - String instance = sharedpreferences.getString(Helper.PREF_INSTANCE, null); SQLiteDatabase db = Sqlite.getInstance(BackupStatusInDataBaseService.this, Sqlite.DB_NAME, null, Sqlite.DB_VERSION).open(); Account account = new AccountDAO(getApplicationContext(), db).getUniqAccount(userId, instance); API api = new API(getApplicationContext(), account.getInstance(), account.getToken()); @@ -126,8 +141,10 @@ public class BackupStatusInDataBaseService extends IntentService { Intent mainActivity = new Intent(BackupStatusInDataBaseService.this, MainActivity.class); mainActivity.putExtra(Helper.INTENT_ACTION, Helper.BACKUP_INTENT); String title = getString(R.string.data_backup_toots, account.getAcct()); - Helper.notify_user(getApplicationContext(),account, mainActivity, BitmapFactory.decodeResource(getResources(), - R.drawable.mastodonlogo), Helper.NotifType.BACKUP, title, message); + if(finalToastMessage) { + Helper.notify_user(getApplicationContext(), account, mainActivity, BitmapFactory.decodeResource(getResources(), + R.drawable.mastodonlogo), Helper.NotifType.BACKUP, title, message); + } } catch (Exception e) { e.printStackTrace(); message = getString(R.string.data_export_error, account.getAcct()); @@ -135,7 +152,9 @@ public class BackupStatusInDataBaseService extends IntentService { new Handler(Looper.getMainLooper()).post(new Runnable() { @Override public void run() { - Toasty.error(getApplicationContext(), finalMessage, Toast.LENGTH_LONG).show(); + if(finalToastMessage) { + Toasty.error(getApplicationContext(), finalMessage, Toast.LENGTH_LONG).show(); + } } }); } diff --git a/app/src/main/res/layout/fragment_settings_reveal.xml b/app/src/main/res/layout/fragment_settings_reveal.xml index d9b61f49c..3a3bc0136 100644 --- a/app/src/main/res/layout/fragment_settings_reveal.xml +++ b/app/src/main/res/layout/fragment_settings_reveal.xml @@ -946,6 +946,41 @@ + + + + + + + + + Charts Display charts The application collects your local data, please wait... + Backup + Auto backup statuses + This option is per account. It will launch a service that will automatically store your statuses locally in the database. That allows to get statistics and charts %d vote %d votes