Browse Source

Convert AccountDao, AccountDataSource and AccountRepository to kotlin

renovate/org.robolectric-robolectric-4.x
Ammar Githam 4 years ago
parent
commit
c647e22293
  1. 1
      app/build.gradle
  2. 31
      app/src/main/java/awais/instagrabber/db/dao/AccountDao.kt
  3. 101
      app/src/main/java/awais/instagrabber/db/datasources/AccountDataSource.kt
  4. 154
      app/src/main/java/awais/instagrabber/db/repositories/AccountRepository.kt
  5. 62
      app/src/main/java/awais/instagrabber/dialogs/AccountSwitcherDialogFragment.java
  6. 18
      app/src/main/java/awais/instagrabber/fragments/main/ProfileFragment.java
  7. 199
      app/src/main/java/awais/instagrabber/fragments/settings/MorePreferencesFragment.java
  8. 10
      app/src/main/java/awais/instagrabber/utils/CookieUtils.kt
  9. 50
      app/src/main/java/awais/instagrabber/utils/ExportImportUtils.java

1
app/build.gradle

@ -195,6 +195,7 @@ dependencies {
def room_version = "2.3.0" def room_version = "2.3.0"
implementation "androidx.room:room-runtime:$room_version" implementation "androidx.room:room-runtime:$room_version"
implementation "androidx.room:room-guava:$room_version" implementation "androidx.room:room-guava:$room_version"
implementation "androidx.room:room-ktx:$room_version"
annotationProcessor "androidx.room:room-compiler:$room_version" annotationProcessor "androidx.room:room-compiler:$room_version"
// CameraX // CameraX

31
app/src/main/java/awais/instagrabber/db/dao/AccountDao.kt

@ -1,34 +1,25 @@
package awais.instagrabber.db.dao;
package awais.instagrabber.db.dao
import androidx.room.Dao;
import androidx.room.Delete;
import androidx.room.Insert;
import androidx.room.OnConflictStrategy;
import androidx.room.Query;
import androidx.room.Update;
import java.util.List;
import awais.instagrabber.db.entities.Account;
import androidx.room.*
import awais.instagrabber.db.entities.Account
@Dao @Dao
public interface AccountDao {
interface AccountDao {
@Query("SELECT * FROM accounts") @Query("SELECT * FROM accounts")
List<Account> getAllAccounts();
suspend fun getAllAccounts(): List<Account>
@Query("SELECT * FROM accounts WHERE uid = :uid") @Query("SELECT * FROM accounts WHERE uid = :uid")
Account findAccountByUid(String uid);
suspend fun findAccountByUid(uid: String): Account?
@Insert(onConflict = OnConflictStrategy.REPLACE) @Insert(onConflict = OnConflictStrategy.REPLACE)
List<Long> insertAccounts(Account... accounts);
suspend fun insertAccounts(vararg accounts: Account): List<Long>
@Update @Update
void updateAccounts(Account... accounts);
suspend fun updateAccounts(vararg accounts: Account)
@Delete @Delete
void deleteAccounts(Account... accounts);
suspend fun deleteAccounts(vararg accounts: Account)
@Query("DELETE from accounts") @Query("DELETE from accounts")
void deleteAllAccounts();
}
suspend fun deleteAllAccounts()
}

101
app/src/main/java/awais/instagrabber/db/datasources/AccountDataSource.kt

@ -1,68 +1,49 @@
package awais.instagrabber.db.datasources;
import android.content.Context;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import java.util.List;
import awais.instagrabber.db.AppDatabase;
import awais.instagrabber.db.dao.AccountDao;
import awais.instagrabber.db.entities.Account;
public class AccountDataSource {
private static final String TAG = AccountDataSource.class.getSimpleName();
package awais.instagrabber.db.datasources
import android.content.Context
import awais.instagrabber.db.AppDatabase
import awais.instagrabber.db.dao.AccountDao
import awais.instagrabber.db.entities.Account
class AccountDataSource private constructor(private val accountDao: AccountDao) {
suspend fun getAccount(uid: String): Account? = accountDao.findAccountByUid(uid)
suspend fun getAllAccounts(): List<Account> = accountDao.getAllAccounts()
suspend fun insertOrUpdateAccount(
uid: String,
username: String,
cookie: String,
fullName: String,
profilePicUrl: String?,
) {
val account = getAccount(uid)
val toUpdate = Account(account?.id ?: 0, uid, username, cookie, fullName, profilePicUrl)
if (account != null) {
accountDao.updateAccounts(toUpdate)
return
}
accountDao.insertAccounts(toUpdate)
}
private static AccountDataSource INSTANCE;
suspend fun deleteAccount(account: Account) = accountDao.deleteAccounts(account)
private final AccountDao accountDao;
suspend fun deleteAllAccounts() = accountDao.deleteAllAccounts()
private AccountDataSource(final AccountDao accountDao) {
this.accountDao = accountDao;
}
companion object {
private lateinit var INSTANCE: AccountDataSource
public static AccountDataSource getInstance(@NonNull Context context) {
if (INSTANCE == null) {
synchronized (AccountDataSource.class) {
if (INSTANCE == null) {
final AppDatabase database = AppDatabase.getDatabase(context);
INSTANCE = new AccountDataSource(database.accountDao());
@JvmStatic
fun getInstance(context: Context): AccountDataSource {
if (!this::INSTANCE.isInitialized) {
synchronized(AccountDataSource::class.java) {
if (!this::INSTANCE.isInitialized) {
val database = AppDatabase.getDatabase(context)
INSTANCE = AccountDataSource(database.accountDao())
}
} }
} }
return INSTANCE
} }
return INSTANCE;
}
@Nullable
public final Account getAccount(final String uid) {
return accountDao.findAccountByUid(uid);
}
@NonNull
public final List<Account> getAllAccounts() {
return accountDao.getAllAccounts();
}
public final void insertOrUpdateAccount(final String uid,
final String username,
final String cookie,
final String fullName,
final String profilePicUrl) {
final Account account = getAccount(uid);
final Account toUpdate = new Account(account == null ? 0 : account.getId(), uid, username, cookie, fullName, profilePicUrl);
if (account != null) {
accountDao.updateAccounts(toUpdate);
return;
}
accountDao.insertAccounts(toUpdate);
}
public final void deleteAccount(@NonNull final Account account) {
accountDao.deleteAccounts(account);
}
public final void deleteAllAccounts() {
accountDao.deleteAllAccounts();
} }
}
}

154
app/src/main/java/awais/instagrabber/db/repositories/AccountRepository.kt

@ -1,131 +1,49 @@
package awais.instagrabber.db.repositories;
package awais.instagrabber.db.repositories
import java.util.List;
import awais.instagrabber.db.datasources.AccountDataSource
import awais.instagrabber.db.entities.Account
import awais.instagrabber.db.datasources.AccountDataSource;
import awais.instagrabber.db.entities.Account;
import awais.instagrabber.utils.AppExecutors;
class AccountRepository private constructor(private val accountDataSource: AccountDataSource) {
suspend fun getAccount(uid: Long): Account? = accountDataSource.getAccount(uid.toString())
public class AccountRepository {
private static final String TAG = AccountRepository.class.getSimpleName();
suspend fun getAllAccounts(): List<Account> = accountDataSource.getAllAccounts()
private static AccountRepository instance;
private final AppExecutors appExecutors;
private final AccountDataSource accountDataSource;
// private List<Account> cachedAccounts;
private AccountRepository(final AppExecutors appExecutors, final AccountDataSource accountDataSource) {
this.appExecutors = appExecutors;
this.accountDataSource = accountDataSource;
}
public static AccountRepository getInstance(final AccountDataSource accountDataSource) {
if (instance == null) {
instance = new AccountRepository(AppExecutors.INSTANCE, accountDataSource);
suspend fun insertOrUpdateAccounts(accounts: List<Account>) {
for (account in accounts) {
accountDataSource.insertOrUpdateAccount(
account.uid,
account.username,
account.cookie,
account.fullName,
account.profilePic
)
} }
return instance;
}
public void getAccount(final long uid,
final RepositoryCallback<Account> callback) {
// request on the I/O thread
appExecutors.getDiskIO().execute(() -> {
final Account account = accountDataSource.getAccount(String.valueOf(uid));
// notify on the main thread
appExecutors.getMainThread().execute(() -> {
if (callback == null) return;
if (account == null) {
callback.onDataNotAvailable();
return;
}
callback.onSuccess(account);
});
});
} }
public void getAllAccounts(final RepositoryCallback<List<Account>> callback) {
// request on the I/O thread
appExecutors.getDiskIO().execute(() -> {
final List<Account> accounts = accountDataSource.getAllAccounts();
// notify on the main thread
appExecutors.getMainThread().execute(() -> {
if (callback == null) return;
if (accounts == null) {
callback.onDataNotAvailable();
return;
}
// cachedAccounts = accounts;
callback.onSuccess(accounts);
});
});
suspend fun insertOrUpdateAccount(
uid: Long,
username: String,
cookie: String,
fullName: String,
profilePicUrl: String?,
): Account? {
accountDataSource.insertOrUpdateAccount(uid.toString(), username, cookie, fullName, profilePicUrl)
return accountDataSource.getAccount(uid.toString())
} }
public void insertOrUpdateAccounts(final List<Account> accounts,
final RepositoryCallback<Void> callback) {
// request on the I/O thread
appExecutors.getDiskIO().execute(() -> {
for (final Account account : accounts) {
accountDataSource.insertOrUpdateAccount(account.getUid(),
account.getUsername(),
account.getCookie(),
account.getFullName(),
account.getProfilePic());
}
// notify on the main thread
appExecutors.getMainThread().execute(() -> {
if (callback == null) return;
callback.onSuccess(null);
});
});
}
suspend fun deleteAccount(account: Account) = accountDataSource.deleteAccount(account)
public void insertOrUpdateAccount(final long uid,
final String username,
final String cookie,
final String fullName,
final String profilePicUrl,
final RepositoryCallback<Account> callback) {
// request on the I/O thread
appExecutors.getDiskIO().execute(() -> {
accountDataSource.insertOrUpdateAccount(String.valueOf(uid), username, cookie, fullName, profilePicUrl);
final Account updated = accountDataSource.getAccount(String.valueOf(uid));
// notify on the main thread
appExecutors.getMainThread().execute(() -> {
if (callback == null) return;
if (updated == null) {
callback.onDataNotAvailable();
return;
}
callback.onSuccess(updated);
});
});
}
suspend fun deleteAllAccounts() = accountDataSource.deleteAllAccounts()
public void deleteAccount(final Account account,
final RepositoryCallback<Void> callback) {
// request on the I/O thread
appExecutors.getDiskIO().execute(() -> {
accountDataSource.deleteAccount(account);
// notify on the main thread
appExecutors.getMainThread().execute(() -> {
if (callback == null) return;
callback.onSuccess(null);
});
});
}
companion object {
private lateinit var instance: AccountRepository
public void deleteAllAccounts(final RepositoryCallback<Void> callback) {
// request on the I/O thread
appExecutors.getDiskIO().execute(() -> {
accountDataSource.deleteAllAccounts();
// notify on the main thread
appExecutors.getMainThread().execute(() -> {
if (callback == null) return;
callback.onSuccess(null);
});
});
@JvmStatic
fun getInstance(accountDataSource: AccountDataSource): AccountRepository {
if (!this::instance.isInitialized) {
instance = AccountRepository(accountDataSource)
}
return instance
}
} }
}
}

62
app/src/main/java/awais/instagrabber/dialogs/AccountSwitcherDialogFragment.java

@ -3,6 +3,7 @@ package awais.instagrabber.dialogs;
import android.app.Dialog; import android.app.Dialog;
import android.content.Context; import android.content.Context;
import android.os.Bundle; import android.os.Bundle;
import android.util.Log;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
@ -14,6 +15,7 @@ import androidx.appcompat.app.AlertDialog;
import androidx.fragment.app.DialogFragment; import androidx.fragment.app.DialogFragment;
import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.LinearLayoutManager;
import java.util.ArrayList;
import java.util.Collections; import java.util.Collections;
import java.util.List; import java.util.List;
@ -23,30 +25,29 @@ import awais.instagrabber.databinding.DialogAccountSwitcherBinding;
import awais.instagrabber.db.datasources.AccountDataSource; import awais.instagrabber.db.datasources.AccountDataSource;
import awais.instagrabber.db.entities.Account; import awais.instagrabber.db.entities.Account;
import awais.instagrabber.db.repositories.AccountRepository; import awais.instagrabber.db.repositories.AccountRepository;
import awais.instagrabber.db.repositories.RepositoryCallback;
import awais.instagrabber.utils.AppExecutors; import awais.instagrabber.utils.AppExecutors;
import awais.instagrabber.utils.Constants; import awais.instagrabber.utils.Constants;
import awais.instagrabber.utils.CookieUtils; import awais.instagrabber.utils.CookieUtils;
import awais.instagrabber.utils.CoroutineUtilsKt;
import awais.instagrabber.utils.ProcessPhoenix; import awais.instagrabber.utils.ProcessPhoenix;
import awais.instagrabber.utils.TextUtils; import awais.instagrabber.utils.TextUtils;
import awais.instagrabber.utils.Utils; import awais.instagrabber.utils.Utils;
import kotlinx.coroutines.Dispatchers;
import static awais.instagrabber.utils.Utils.settingsHelper; import static awais.instagrabber.utils.Utils.settingsHelper;
public class AccountSwitcherDialogFragment extends DialogFragment { public class AccountSwitcherDialogFragment extends DialogFragment {
private static final String TAG = AccountSwitcherDialogFragment.class.getSimpleName();
private AccountRepository accountRepository; private AccountRepository accountRepository;
private OnAddAccountClickListener onAddAccountClickListener; private OnAddAccountClickListener onAddAccountClickListener;
private DialogAccountSwitcherBinding binding; private DialogAccountSwitcherBinding binding;
public AccountSwitcherDialogFragment() {
accountRepository = AccountRepository.getInstance(AccountDataSource.getInstance(getContext()));
}
public AccountSwitcherDialogFragment() {}
public AccountSwitcherDialogFragment(final OnAddAccountClickListener onAddAccountClickListener) { public AccountSwitcherDialogFragment(final OnAddAccountClickListener onAddAccountClickListener) {
this.onAddAccountClickListener = onAddAccountClickListener; this.onAddAccountClickListener = onAddAccountClickListener;
accountRepository = AccountRepository.getInstance(AccountDataSource.getInstance(getContext()));
} }
private final AccountSwitcherAdapter.OnAccountClickListener accountClickListener = (model, isCurrent) -> { private final AccountSwitcherAdapter.OnAccountClickListener accountClickListener = (model, isCurrent) -> {
@ -80,17 +81,15 @@ public class AccountSwitcherDialogFragment extends DialogFragment {
.setMessage(getString(R.string.quick_access_confirm_delete, model.getUsername())) .setMessage(getString(R.string.quick_access_confirm_delete, model.getUsername()))
.setPositiveButton(R.string.yes, (dialog, which) -> { .setPositiveButton(R.string.yes, (dialog, which) -> {
if (accountRepository == null) return; if (accountRepository == null) return;
accountRepository.deleteAccount(model, new RepositoryCallback<Void>() {
@Override
public void onSuccess(final Void result) {
dismiss();
}
@Override
public void onDataNotAvailable() {
dismiss();
}
});
accountRepository.deleteAccount(
model,
CoroutineUtilsKt.getContinuation((unit, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
dismiss();
if (throwable != null) {
Log.e(TAG, "deleteAccount: ", throwable);
}
}), Dispatchers.getIO())
);
}) })
.setNegativeButton(R.string.cancel, null) .setNegativeButton(R.string.cancel, null)
.show(); .show();
@ -113,6 +112,12 @@ public class AccountSwitcherDialogFragment extends DialogFragment {
init(); init();
} }
@Override
public void onAttach(@NonNull final Context context) {
super.onAttach(context);
accountRepository = AccountRepository.getInstance(AccountDataSource.getInstance(context));
}
@Override @Override
public void onStart() { public void onStart() {
super.onStart(); super.onStart();
@ -129,18 +134,19 @@ public class AccountSwitcherDialogFragment extends DialogFragment {
final AccountSwitcherAdapter adapter = new AccountSwitcherAdapter(accountClickListener, accountLongClickListener); final AccountSwitcherAdapter adapter = new AccountSwitcherAdapter(accountClickListener, accountLongClickListener);
binding.accounts.setAdapter(adapter); binding.accounts.setAdapter(adapter);
if (accountRepository == null) return; if (accountRepository == null) return;
accountRepository.getAllAccounts(new RepositoryCallback<List<Account>>() {
@Override
public void onSuccess(final List<Account> accounts) {
if (accounts == null) return;
final String cookie = settingsHelper.getString(Constants.COOKIE);
sortUserList(cookie, accounts);
adapter.submitList(accounts);
}
@Override
public void onDataNotAvailable() {}
});
accountRepository.getAllAccounts(
CoroutineUtilsKt.getContinuation((accounts, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
if (throwable != null) {
Log.e(TAG, "init: ", throwable);
return;
}
if (accounts == null) return;
final String cookie = settingsHelper.getString(Constants.COOKIE);
final List<Account> copy = new ArrayList<>(accounts);
sortUserList(cookie, copy);
adapter.submitList(copy);
}), Dispatchers.getIO())
);
binding.addAccountBtn.setOnClickListener(v -> { binding.addAccountBtn.setOnClickListener(v -> {
if (onAddAccountClickListener == null) return; if (onAddAccountClickListener == null) return;
onAddAccountClickListener.onAddAccountClick(this); onAddAccountClickListener.onAddAccountClick(this);

18
app/src/main/java/awais/instagrabber/fragments/main/ProfileFragment.java

@ -62,7 +62,6 @@ import awais.instagrabber.databinding.FragmentProfileBinding;
import awais.instagrabber.databinding.LayoutProfileDetailsBinding; import awais.instagrabber.databinding.LayoutProfileDetailsBinding;
import awais.instagrabber.db.datasources.AccountDataSource; import awais.instagrabber.db.datasources.AccountDataSource;
import awais.instagrabber.db.datasources.FavoriteDataSource; import awais.instagrabber.db.datasources.FavoriteDataSource;
import awais.instagrabber.db.entities.Account;
import awais.instagrabber.db.entities.Favorite; import awais.instagrabber.db.entities.Favorite;
import awais.instagrabber.db.repositories.AccountRepository; import awais.instagrabber.db.repositories.AccountRepository;
import awais.instagrabber.db.repositories.FavoriteRepository; import awais.instagrabber.db.repositories.FavoriteRepository;
@ -1027,17 +1026,14 @@ public class ProfileFragment extends Fragment implements SwipeRefreshLayout.OnRe
cookie, cookie,
profileModel.getFullName(), profileModel.getFullName(),
profileModel.getProfilePicUrl(), profileModel.getProfilePicUrl(),
new RepositoryCallback<Account>() {
@Override
public void onSuccess(final Account result) {
accountIsUpdated = true;
}
@Override
public void onDataNotAvailable() {
Log.e(TAG, "onDataNotAvailable: insert failed");
CoroutineUtilsKt.getContinuation((account, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
if (throwable != null) {
Log.e(TAG, "updateAccountInfo: ", throwable);
return;
} }
});
accountIsUpdated = true;
}), Dispatchers.getIO())
);
} }
private void fetchStoryAndHighlights(final long profileId) { private void fetchStoryAndHighlights(final long profileId) {

199
app/src/main/java/awais/instagrabber/fragments/settings/MorePreferencesFragment.java

@ -11,7 +11,6 @@ import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
import android.widget.Toast; import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable; import androidx.annotation.Nullable;
import androidx.appcompat.app.AlertDialog; import androidx.appcompat.app.AlertDialog;
import androidx.fragment.app.FragmentManager; import androidx.fragment.app.FragmentManager;
@ -24,17 +23,13 @@ import androidx.preference.PreferenceScreen;
import androidx.preference.PreferenceViewHolder; import androidx.preference.PreferenceViewHolder;
import androidx.recyclerview.widget.RecyclerView; import androidx.recyclerview.widget.RecyclerView;
import java.util.List;
import awais.instagrabber.BuildConfig; import awais.instagrabber.BuildConfig;
import awais.instagrabber.R; import awais.instagrabber.R;
import awais.instagrabber.activities.Login; import awais.instagrabber.activities.Login;
import awais.instagrabber.activities.MainActivity; import awais.instagrabber.activities.MainActivity;
import awais.instagrabber.databinding.PrefAccountSwitcherBinding; import awais.instagrabber.databinding.PrefAccountSwitcherBinding;
import awais.instagrabber.db.datasources.AccountDataSource; import awais.instagrabber.db.datasources.AccountDataSource;
import awais.instagrabber.db.entities.Account;
import awais.instagrabber.db.repositories.AccountRepository; import awais.instagrabber.db.repositories.AccountRepository;
import awais.instagrabber.db.repositories.RepositoryCallback;
import awais.instagrabber.dialogs.AccountSwitcherDialogFragment; import awais.instagrabber.dialogs.AccountSwitcherDialogFragment;
import awais.instagrabber.utils.AppExecutors; import awais.instagrabber.utils.AppExecutors;
import awais.instagrabber.utils.Constants; import awais.instagrabber.utils.Constants;
@ -98,75 +93,77 @@ public class MorePreferencesFragment extends BasePreferencesFragment {
return true; return true;
})); }));
} }
accountRepository.getAllAccounts(new RepositoryCallback<List<Account>>() {
@Override
public void onSuccess(@NonNull final List<Account> accounts) {
if (!isLoggedIn) {
accountRepository.getAllAccounts(
CoroutineUtilsKt.getContinuation((accounts, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
if (throwable != null) {
Log.d(TAG, "getAllAccounts", throwable);
if (!isLoggedIn) {
// Need to show something to trigger login activity
accountCategory.addPreference(getPreference(R.string.add_account, R.drawable.ic_add, preference -> {
startActivityForResult(new Intent(getContext(), Login.class), Constants.LOGIN_RESULT_CODE);
return true;
}));
}
return;
}
if (!isLoggedIn) {
if (accounts.size() > 0) {
final Context context1 = getContext();
final AccountSwitcherPreference preference = getAccountSwitcherPreference(null, context1);
if (preference == null) return;
accountCategory.addPreference(preference);
}
// Need to show something to trigger login activity
final Preference preference1 = getPreference(R.string.add_account, R.drawable.ic_add, preference -> {
final Context context1 = getContext();
if (context1 == null) return false;
startActivityForResult(new Intent(context1, Login.class), Constants.LOGIN_RESULT_CODE);
return true;
});
if (preference1 == null) return;
accountCategory.addPreference(preference1);
}
if (accounts.size() > 0) { if (accounts.size() > 0) {
final Context context1 = getContext();
final AccountSwitcherPreference preference = getAccountSwitcherPreference(null, context1);
if (preference == null) return;
accountCategory.addPreference(preference);
final Preference preference1 = getPreference(
R.string.remove_all_acc,
null,
R.drawable.ic_account_multiple_remove_24,
preference -> {
if (getContext() == null) return false;
new AlertDialog.Builder(getContext())
.setTitle(R.string.logout)
.setMessage(R.string.remove_all_acc_warning)
.setPositiveButton(R.string.yes, (dialog, which) -> {
final Context context1 = getContext();
if (context1 == null) return;
CookieUtils.removeAllAccounts(
context1,
CoroutineUtilsKt.getContinuation(
(unit, throwable1) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
if (throwable1 != null) {
return;
}
final Context context2 = getContext();
if (context2 == null) return;
Toast.makeText(context2, R.string.logout_success, Toast.LENGTH_SHORT).show();
settingsHelper.putString(Constants.COOKIE, "");
AppExecutors.INSTANCE
.getMainThread()
.execute(() -> ProcessPhoenix.triggerRebirth(context1), 200);
}),
Dispatchers.getIO()
)
);
})
.setNegativeButton(R.string.cancel, null)
.show();
return true;
});
if (preference1 == null) return;
accountCategory.addPreference(preference1);
} }
// Need to show something to trigger login activity
final Preference preference1 = getPreference(R.string.add_account, R.drawable.ic_add, preference -> {
final Context context1 = getContext();
if (context1 == null) return false;
startActivityForResult(new Intent(context1, Login.class), Constants.LOGIN_RESULT_CODE);
return true;
});
if (preference1 == null) return;
accountCategory.addPreference(preference1);
}
if (accounts.size() > 0) {
final Preference preference1 = getPreference(
R.string.remove_all_acc,
null,
R.drawable.ic_account_multiple_remove_24,
preference -> {
if (getContext() == null) return false;
new AlertDialog.Builder(getContext())
.setTitle(R.string.logout)
.setMessage(R.string.remove_all_acc_warning)
.setPositiveButton(R.string.yes, (dialog, which) -> {
final Context context1 = getContext();
if (context1 == null) return;
CookieUtils.removeAllAccounts(context1, new RepositoryCallback<Void>() {
@Override
public void onSuccess(final Void result) {
// shouldRecreate();
final Context context1 = getContext();
if (context1 == null) return;
Toast.makeText(context1, R.string.logout_success, Toast.LENGTH_SHORT).show();
settingsHelper.putString(Constants.COOKIE, "");
AppExecutors.INSTANCE.getMainThread().execute(() -> ProcessPhoenix.triggerRebirth(context1), 200);
}
@Override
public void onDataNotAvailable() {}
});
})
.setNegativeButton(R.string.cancel, null)
.show();
return true;
});
if (preference1 == null) return;
accountCategory.addPreference(preference1);
}
}
@Override
public void onDataNotAvailable() {
Log.d(TAG, "onDataNotAvailable");
if (!isLoggedIn) {
// Need to show something to trigger login activity
accountCategory.addPreference(getPreference(R.string.add_account, R.drawable.ic_add, preference -> {
startActivityForResult(new Intent(getContext(), Login.class), Constants.LOGIN_RESULT_CODE);
return true;
}));
}
}
});
}), Dispatchers.getIO())
);
// final PreferenceCategory generalCategory = new PreferenceCategory(context); // final PreferenceCategory generalCategory = new PreferenceCategory(context);
// generalCategory.setTitle(R.string.pref_category_general); // generalCategory.setTitle(R.string.pref_category_general);
@ -295,31 +292,24 @@ public class MorePreferencesFragment extends BasePreferencesFragment {
return; return;
} }
if (user != null) { if (user != null) {
// Log.d(TAG, "adding userInfo: " + result);
accountRepository.insertOrUpdateAccount( accountRepository.insertOrUpdateAccount(
uid, uid,
user.getUsername(), user.getUsername(),
cookie, cookie,
user.getFullName(), user.getFullName(),
user.getProfilePicUrl(), user.getProfilePicUrl(),
new RepositoryCallback<Account>() {
@Override
public void onSuccess(final Account result) {
// final FragmentActivity activity = getActivity();
// if (activity == null) return;
// activity.recreate();
AppExecutors.INSTANCE.getMainThread().execute(() -> {
final Context context = getContext();
if (context == null) return;
ProcessPhoenix.triggerRebirth(context);
}, 200);
CoroutineUtilsKt.getContinuation((account, throwable1) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
if (throwable1 != null) {
Log.e(TAG, "onActivityResult: ", throwable1);
return;
} }
@Override
public void onDataNotAvailable() {
Log.e(TAG, "onDataNotAvailable: insert failed");
}
});
AppExecutors.INSTANCE.getMainThread().execute(() -> {
final Context context = getContext();
if (context == null) return;
ProcessPhoenix.triggerRebirth(context);
}, 200);
}), Dispatchers.getIO())
);
} }
}), Dispatchers.getIO())); }), Dispatchers.getIO()));
} }
@ -415,20 +405,21 @@ public class MorePreferencesFragment extends BasePreferencesFragment {
final PrefAccountSwitcherBinding binding = PrefAccountSwitcherBinding.bind(root); final PrefAccountSwitcherBinding binding = PrefAccountSwitcherBinding.bind(root);
final long uid = CookieUtils.getUserIdFromCookie(cookie); final long uid = CookieUtils.getUserIdFromCookie(cookie);
if (uid <= 0) return; if (uid <= 0) return;
accountRepository.getAccount(uid, new RepositoryCallback<Account>() {
@Override
public void onSuccess(final Account account) {
binding.getRoot().post(() -> {
binding.fullName.setText(account.getFullName());
binding.username.setText("@" + account.getUsername());
binding.profilePic.setImageURI(account.getProfilePic());
binding.getRoot().requestLayout();
});
}
@Override
public void onDataNotAvailable() {}
});
accountRepository.getAccount(
uid,
CoroutineUtilsKt.getContinuation((account, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
if (throwable != null) {
Log.e(TAG, "onBindViewHolder: ", throwable);
return;
}
binding.getRoot().post(() -> {
binding.fullName.setText(account.getFullName());
binding.username.setText("@" + account.getUsername());
binding.profilePic.setImageURI(account.getProfilePic());
binding.getRoot().requestLayout();
});
}), Dispatchers.getIO())
);
} }
} }
} }

10
app/src/main/java/awais/instagrabber/utils/CookieUtils.kt

@ -7,7 +7,6 @@ import android.util.Log
import android.webkit.CookieManager import android.webkit.CookieManager
import awais.instagrabber.db.datasources.AccountDataSource import awais.instagrabber.db.datasources.AccountDataSource
import awais.instagrabber.db.repositories.AccountRepository import awais.instagrabber.db.repositories.AccountRepository
import awais.instagrabber.db.repositories.RepositoryCallback
import java.net.CookiePolicy import java.net.CookiePolicy
import java.net.HttpCookie import java.net.HttpCookie
import java.net.URI import java.net.URI
@ -48,14 +47,9 @@ fun setupCookies(cookieRaw: String) {
} }
} }
fun removeAllAccounts(context: Context, callback: RepositoryCallback<Void?>?) {
suspend fun removeAllAccounts(context: Context) {
NET_COOKIE_MANAGER.cookieStore.removeAll() NET_COOKIE_MANAGER.cookieStore.removeAll()
try {
AccountRepository.getInstance(AccountDataSource.getInstance(context))
.deleteAllAccounts(callback)
} catch (e: Exception) {
Log.e(TAG, "setupCookies", e)
}
AccountRepository.getInstance(AccountDataSource.getInstance(context)).deleteAllAccounts()
} }
fun getUserIdFromCookie(cookies: String?): Long { fun getUserIdFromCookie(cookies: String?): Long {

50
app/src/main/java/awais/instagrabber/utils/ExportImportUtils.java

@ -42,6 +42,7 @@ import awais.instagrabber.db.repositories.RepositoryCallback;
import awais.instagrabber.interfaces.FetchListener; import awais.instagrabber.interfaces.FetchListener;
import awais.instagrabber.models.enums.FavoriteType; import awais.instagrabber.models.enums.FavoriteType;
import awais.instagrabber.utils.PasswordUtils.IncorrectPasswordException; import awais.instagrabber.utils.PasswordUtils.IncorrectPasswordException;
import kotlinx.coroutines.Dispatchers;
import static awais.instagrabber.utils.Utils.settingsHelper; import static awais.instagrabber.utils.Utils.settingsHelper;
@ -396,33 +397,32 @@ public final class ExportImportUtils {
private static ListenableFuture<JSONArray> getCookies(final Context context) { private static ListenableFuture<JSONArray> getCookies(final Context context) {
final SettableFuture<JSONArray> future = SettableFuture.create(); final SettableFuture<JSONArray> future = SettableFuture.create();
final AccountRepository accountRepository = AccountRepository.getInstance(AccountDataSource.getInstance(context)); final AccountRepository accountRepository = AccountRepository.getInstance(AccountDataSource.getInstance(context));
accountRepository.getAllAccounts(new RepositoryCallback<List<Account>>() {
@Override
public void onSuccess(final List<Account> accounts) {
final JSONArray jsonArray = new JSONArray();
try {
for (final Account cookie : accounts) {
final JSONObject jsonObject = new JSONObject();
jsonObject.put("i", cookie.getUid());
jsonObject.put("u", cookie.getUsername());
jsonObject.put("c", cookie.getCookie());
jsonObject.put("full_name", cookie.getFullName());
jsonObject.put("profile_pic", cookie.getProfilePic());
jsonArray.put(jsonObject);
accountRepository.getAllAccounts(
CoroutineUtilsKt.getContinuation((accounts, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
if (throwable != null) {
Log.e(TAG, "getCookies: ", throwable);
future.set(new JSONArray());
return;
} }
} catch (Exception e) {
if (BuildConfig.DEBUG) {
Log.e(TAG, "Error exporting accounts", e);
final JSONArray jsonArray = new JSONArray();
try {
for (final Account cookie : accounts) {
final JSONObject jsonObject = new JSONObject();
jsonObject.put("i", cookie.getUid());
jsonObject.put("u", cookie.getUsername());
jsonObject.put("c", cookie.getCookie());
jsonObject.put("full_name", cookie.getFullName());
jsonObject.put("profile_pic", cookie.getProfilePic());
jsonArray.put(jsonObject);
}
} catch (Exception e) {
if (BuildConfig.DEBUG) {
Log.e(TAG, "Error exporting accounts", e);
}
} }
}
future.set(jsonArray);
}
@Override
public void onDataNotAvailable() {
future.set(new JSONArray());
}
});
future.set(jsonArray);
}), Dispatchers.getIO())
);
return future; return future;
} }

Loading…
Cancel
Save