From 9f61359c43643f311ae9690110d0ac295942a6a9 Mon Sep 17 00:00:00 2001 From: Adithya Abraham Philip Date: Sat, 20 Jun 2015 16:54:33 +0530 Subject: [PATCH] introduced OperationHelper --- .../remote/ui/AccountSettingsFragment.java | 2 +- .../keychain/service/KeychainNewService.java | 3 +- .../keychain/ui/EditKeyFragment.java | 57 ++-- .../keychain/ui/EncryptFilesFragment.java | 2 +- .../keychain/ui/ImportKeysActivity.java | 72 +++-- .../ui/base/CryptoOperationFragment.java | 19 +- .../ui/base/NewCryptoOperationFragment.java | 74 ++++++ .../keychain/util/FileHelper.java | 6 +- .../keychain/util/OperationHelper.java | 247 ++++++++++++++++++ 9 files changed, 389 insertions(+), 93 deletions(-) create mode 100644 OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/base/NewCryptoOperationFragment.java create mode 100644 OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/OperationHelper.java diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/AccountSettingsFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/AccountSettingsFragment.java index 18afd2f23..d2ede2e67 100644 --- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/AccountSettingsFragment.java +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/AccountSettingsFragment.java @@ -116,7 +116,7 @@ public class AccountSettingsFragment extends Fragment { } } - // execute activity's onActivityResult to show log notify + // execute activity's handleActivityResult to show log notify super.onActivityResult(requestCode, resultCode, data); } } diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainNewService.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainNewService.java index eaf48ddbd..d6a148cfe 100644 --- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainNewService.java +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainNewService.java @@ -103,8 +103,7 @@ public class KeychainNewService extends Service implements Progressable { } else if (inputParcel instanceof ImportKeyringParcel) { op = new ImportExportOperation(outerThis, new ProviderHelper(outerThis), outerThis, mActionCanceled); - } - else { + } else { return; } diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EditKeyFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EditKeyFragment.java index 48aa3016d..cf975c4f3 100644 --- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EditKeyFragment.java +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EditKeyFragment.java @@ -18,7 +18,6 @@ package org.sufficientlysecure.keychain.ui; import android.app.Activity; -import android.app.ProgressDialog; import android.content.Intent; import android.database.Cursor; import android.net.Uri; @@ -26,7 +25,6 @@ import android.os.Bundle; import android.os.Handler; import android.os.Message; import android.os.Messenger; -import android.os.Parcelable; import android.support.v4.app.LoaderManager; import android.support.v4.content.CursorLoader; import android.support.v4.content.Loader; @@ -40,9 +38,6 @@ import android.widget.ListView; import org.sufficientlysecure.keychain.Constants; import org.sufficientlysecure.keychain.R; import org.sufficientlysecure.keychain.compatibility.DialogFragmentWorkaround; -import org.sufficientlysecure.keychain.operations.results.DecryptVerifyResult; -import org.sufficientlysecure.keychain.operations.results.EditKeyResult; -import org.sufficientlysecure.keychain.operations.results.InputPendingResult; import org.sufficientlysecure.keychain.operations.results.OperationResult; import org.sufficientlysecure.keychain.operations.results.OperationResult.LogType; import org.sufficientlysecure.keychain.operations.results.SingletonResult; @@ -54,8 +49,6 @@ import org.sufficientlysecure.keychain.provider.KeychainContract; import org.sufficientlysecure.keychain.provider.KeychainContract.UserPackets; import org.sufficientlysecure.keychain.provider.ProviderHelper; import org.sufficientlysecure.keychain.provider.ProviderHelper.NotFoundException; -import org.sufficientlysecure.keychain.service.KeychainService; -import org.sufficientlysecure.keychain.service.ServiceProgressHandler; import org.sufficientlysecure.keychain.service.SaveKeyringParcel; import org.sufficientlysecure.keychain.service.SaveKeyringParcel.ChangeUnlockParcel; import org.sufficientlysecure.keychain.service.SaveKeyringParcel.SubkeyChange; @@ -64,13 +57,19 @@ import org.sufficientlysecure.keychain.ui.adapter.SubkeysAdapter; import org.sufficientlysecure.keychain.ui.adapter.SubkeysAddedAdapter; import org.sufficientlysecure.keychain.ui.adapter.UserIdsAdapter; import org.sufficientlysecure.keychain.ui.adapter.UserIdsAddedAdapter; -import org.sufficientlysecure.keychain.ui.base.CryptoOperationFragment; -import org.sufficientlysecure.keychain.ui.dialog.*; +import org.sufficientlysecure.keychain.ui.base.NewCryptoOperationFragment; +import org.sufficientlysecure.keychain.ui.dialog.AddSubkeyDialogFragment; +import org.sufficientlysecure.keychain.ui.dialog.AddUserIdDialogFragment; +import org.sufficientlysecure.keychain.ui.dialog.EditSubkeyDialogFragment; +import org.sufficientlysecure.keychain.ui.dialog.EditSubkeyExpiryDialogFragment; +import org.sufficientlysecure.keychain.ui.dialog.EditUserIdDialogFragment; +import org.sufficientlysecure.keychain.ui.dialog.SetPassphraseDialogFragment; import org.sufficientlysecure.keychain.ui.util.Notify; import org.sufficientlysecure.keychain.util.Log; +import org.sufficientlysecure.keychain.util.OperationHelper; import org.sufficientlysecure.keychain.util.Passphrase; -public class EditKeyFragment extends CryptoOperationFragment +public class EditKeyFragment extends NewCryptoOperationFragment implements LoaderManager.LoaderCallbacks { public static final String ARG_DATA_URI = "uri"; @@ -144,6 +143,27 @@ public class EditKeyFragment extends CryptoOperationFragment(getActivity()) { + + @Override + public SaveKeyringParcel createOperationInput() { + return mSaveKeyringParcel; + } + + @Override + protected void onCryptoOperationSuccess(OperationResult result) { + + // if good -> finish, return result to showkey and display there! + Intent intent = new Intent(); + intent.putExtra(OperationResult.EXTRA_RESULT, result); + getActivity().setResult(EditKeyActivity.RESULT_OK, intent); + getActivity().finish(); + } + } + ); + ((EditKeyActivity) getActivity()).setFullScreenDialogDoneClose( R.string.btn_save, new OnClickListener() { @@ -607,21 +627,4 @@ public class EditKeyFragment extends CryptoOperationFragment finish, return result to showkey and display there! - Intent intent = new Intent(); - intent.putExtra(OperationResult.EXTRA_RESULT, result); - getActivity().setResult(EditKeyActivity.RESULT_OK, intent); - getActivity().finish(); - - } - } diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesFragment.java index d290c57a6..e2d353cc5 100644 --- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesFragment.java +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesFragment.java @@ -465,7 +465,7 @@ public class EncryptFilesFragment if (actionsParcel.isIncomplete()) { // if this is still null, prepare output streams again if (mOutputUris == null) { - // this may interrupt the flow, and call us again from onActivityResult + // this may interrupt the flow, and call us again from handleActivityResult if (prepareOutputStreams(mShareAfterEncrypt)) { return null; } diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysActivity.java index ea0d3a318..f3c11a785 100644 --- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysActivity.java +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysActivity.java @@ -35,7 +35,10 @@ import org.sufficientlysecure.keychain.keyimport.ImportKeysListEntry; import org.sufficientlysecure.keychain.keyimport.ParcelableKeyRing; import org.sufficientlysecure.keychain.operations.results.ImportKeyResult; import org.sufficientlysecure.keychain.operations.results.OperationResult; +import org.sufficientlysecure.keychain.service.ImportKeyringParcel; +import org.sufficientlysecure.keychain.service.KeychainNewService; import org.sufficientlysecure.keychain.service.KeychainService; +import org.sufficientlysecure.keychain.service.input.CryptoInputParcel; import org.sufficientlysecure.keychain.ui.base.BaseNfcActivity; import org.sufficientlysecure.keychain.service.ServiceProgressHandler; import org.sufficientlysecure.keychain.ui.util.KeyFormattingUtils; @@ -373,8 +376,7 @@ public class ImportKeysActivity extends BaseNfcActivity { if (returnData == null) { return; } - final ImportKeyResult result = - returnData.getParcelable(OperationResult.EXTRA_RESULT); + final ImportKeyResult result = returnData.getParcelable(OperationResult.EXTRA_RESULT); if (result == null) { Log.e(Constants.TAG, "result == null"); return; @@ -421,12 +423,9 @@ public class ImportKeysActivity extends BaseNfcActivity { }; // Send all information needed to service to import key in other thread - Intent intent = new Intent(this, KeychainService.class); - - intent.setAction(KeychainService.ACTION_IMPORT_KEYRING); - - // fill values for this action - Bundle data = new Bundle(); + Intent intent = new Intent(this, KeychainNewService.class); + ImportKeyringParcel operationInput = null; + CryptoInputParcel cryptoInput = null; ImportKeysListFragment.LoaderState ls = mListFragment.getLoaderState(); if (ls instanceof ImportKeysListFragment.BytesLoaderState) { @@ -445,21 +444,9 @@ public class ImportKeysActivity extends BaseNfcActivity { new ParcelableFileCache<>(this, "key_import.pcl"); cache.writeCache(selectedEntries); - intent.putExtra(KeychainService.EXTRA_DATA, data); + operationInput = new ImportKeyringParcel(null, null); + cryptoInput = new CryptoInputParcel(); - // Create a new Messenger for the communication back - Messenger messenger = new Messenger(serviceHandler); - intent.putExtra(KeychainService.EXTRA_MESSENGER, messenger); - - // show progress dialog - serviceHandler.showProgressDialog( - getString(R.string.progress_importing), - ProgressDialog.STYLE_HORIZONTAL, - true - ); - - // start service with intent - startService(intent); } catch (IOException e) { Log.e(Constants.TAG, "Problem writing cache file", e); Notify.create(this, "Problem writing cache file!", Notify.Style.ERROR) @@ -468,10 +455,6 @@ public class ImportKeysActivity extends BaseNfcActivity { } else if (ls instanceof ImportKeysListFragment.CloudLoaderState) { ImportKeysListFragment.CloudLoaderState sls = (ImportKeysListFragment.CloudLoaderState) ls; - data.putString(KeychainService.IMPORT_KEY_SERVER, sls.mCloudPrefs.keyserver); - - data.putParcelable(KeychainService.EXTRA_PARCELABLE_PROXY, mProxyPrefs.parcelableProxy); - // get selected key entries ArrayList keys = new ArrayList<>(); { @@ -483,23 +466,30 @@ public class ImportKeysActivity extends BaseNfcActivity { ); } } - data.putParcelableArrayList(KeychainService.IMPORT_KEY_LIST, keys); - intent.putExtra(KeychainService.EXTRA_DATA, data); - - // Create a new Messenger for the communication back - Messenger messenger = new Messenger(serviceHandler); - intent.putExtra(KeychainService.EXTRA_MESSENGER, messenger); - - // show progress dialog - serviceHandler.showProgressDialog( - getString(R.string.progress_importing), - ProgressDialog.STYLE_HORIZONTAL, true - ); - - // start service with intent - startService(intent); + operationInput = new ImportKeyringParcel(keys, sls.mCloudPrefs.keyserver); + if (mProxyPrefs != null) { // if not null means we have specified an explicit proxy + cryptoInput = new CryptoInputParcel(mProxyPrefs.parcelableProxy); + } else { + cryptoInput = new CryptoInputParcel(); + } } + + intent.putExtra(KeychainNewService.EXTRA_OPERATION_INPUT, operationInput); + intent.putExtra(KeychainNewService.EXTRA_CRYPTO_INPUT, cryptoInput); + + // Create a new Messenger for the communication back + Messenger messenger = new Messenger(serviceHandler); + intent.putExtra(KeychainService.EXTRA_MESSENGER, messenger); + + // show progress dialog + serviceHandler.showProgressDialog( + getString(R.string.progress_importing), + ProgressDialog.STYLE_HORIZONTAL, true + ); + + // start service with intent + startService(intent); } @Override diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/base/CryptoOperationFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/base/CryptoOperationFragment.java index 28d9d4935..1a59b1cba 100644 --- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/base/CryptoOperationFragment.java +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/base/CryptoOperationFragment.java @@ -36,10 +36,8 @@ import org.sufficientlysecure.keychain.service.ServiceProgressHandler; import org.sufficientlysecure.keychain.service.input.CryptoInputParcel; import org.sufficientlysecure.keychain.service.input.RequiredInputParcel; import org.sufficientlysecure.keychain.ui.NfcOperationActivity; -import org.sufficientlysecure.keychain.ui.OrbotRequiredDialogActivity; import org.sufficientlysecure.keychain.ui.PassphraseDialogActivity; import org.sufficientlysecure.keychain.ui.dialog.ProgressDialogFragment; -import org.sufficientlysecure.keychain.util.orbot.OrbotHelper; /** @@ -50,7 +48,6 @@ public abstract class CryptoOperationFragment + * Copyright (C) 2015 Vincent Breitmoser + * + * 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. + * + * This program 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 this program. If not, see . + */ + +package org.sufficientlysecure.keychain.ui.base; + +import android.app.Activity; +import android.app.ProgressDialog; +import android.content.Intent; +import android.os.Bundle; +import android.os.Message; +import android.os.Messenger; +import android.os.Parcelable; +import android.support.v4.app.Fragment; + +import org.sufficientlysecure.keychain.R; +import org.sufficientlysecure.keychain.operations.results.InputPendingResult; +import org.sufficientlysecure.keychain.operations.results.OperationResult; +import org.sufficientlysecure.keychain.service.KeychainNewService; +import org.sufficientlysecure.keychain.service.KeychainService; +import org.sufficientlysecure.keychain.service.ServiceProgressHandler; +import org.sufficientlysecure.keychain.service.input.CryptoInputParcel; +import org.sufficientlysecure.keychain.service.input.RequiredInputParcel; +import org.sufficientlysecure.keychain.ui.NfcOperationActivity; +import org.sufficientlysecure.keychain.ui.OrbotRequiredDialogActivity; +import org.sufficientlysecure.keychain.ui.PassphraseDialogActivity; +import org.sufficientlysecure.keychain.ui.dialog.ProgressDialogFragment; +import org.sufficientlysecure.keychain.util.Log; +import org.sufficientlysecure.keychain.util.OperationHelper; +import org.sufficientlysecure.keychain.util.orbot.OrbotHelper; + + +/** + * All fragments executing crypto operations need to extend this class. + */ +public abstract class NewCryptoOperationFragment + extends Fragment { + + private OperationHelper mOperationHelper; + + @Override + public void onActivityResult(int requestCode, int resultCode, Intent data) { + Log.d("PHILIP", "requestCode "+ requestCode + " resultCode" + resultCode); + if (!mOperationHelper.handleActivityResult(requestCode, resultCode, data)) { + super.onActivityResult(requestCode, resultCode, data); + } + } + + protected void setOperationHelper(OperationHelper helper) { + mOperationHelper = helper; + } + + protected void cryptoOperation() { + mOperationHelper.cryptoOperation(); + } + + protected void cryptoOperation(CryptoInputParcel inputParcel) { + mOperationHelper.cryptoOperation(inputParcel); + } +} diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/FileHelper.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/FileHelper.java index 677acb1b8..9d072cc50 100644 --- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/FileHelper.java +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/FileHelper.java @@ -70,7 +70,7 @@ public class FileHelper { * @param last default selected Uri, not supported by all file managers * @param mimeType can be text/plain for example * @param requestCode requestCode used to identify the result coming back from file manager to - * onActivityResult() in your activity + * handleActivityResult() in your activity */ public static void openFile(Fragment fragment, Uri last, String mimeType, int requestCode) { Intent intent = new Intent(Intent.ACTION_GET_CONTENT); @@ -144,7 +144,7 @@ public class FileHelper { * @param fragment * @param mimeType can be text/plain for example * @param multiple allow file chooser to return multiple files - * @param requestCode used to identify the result coming back from storage browser onActivityResult() in your + * @param requestCode used to identify the result coming back from storage browser handleActivityResult() in your */ @TargetApi(Build.VERSION_CODES.KITKAT) public static void openDocument(Fragment fragment, String mimeType, boolean multiple, int requestCode) { @@ -162,7 +162,7 @@ public class FileHelper { * @param fragment * @param mimeType can be text/plain for example * @param suggestedName a filename desirable for the file to be saved - * @param requestCode used to identify the result coming back from storage browser onActivityResult() in your + * @param requestCode used to identify the result coming back from storage browser handleActivityResult() in your */ @TargetApi(Build.VERSION_CODES.KITKAT) public static void saveDocument(Fragment fragment, String mimeType, String suggestedName, int requestCode) { diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/OperationHelper.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/OperationHelper.java new file mode 100644 index 000000000..11045cc24 --- /dev/null +++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/OperationHelper.java @@ -0,0 +1,247 @@ +/* + * Copyright (C) 2015 Dominik Schürmann + * Copyright (C) 2015 Vincent Breitmoser + * Copyright (C) 2015 Adithya Abraham Philip + * + * 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. + * + * This program 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 this program. If not, see . + */ + +package org.sufficientlysecure.keychain.util; + +import android.app.Activity; +import android.app.ProgressDialog; +import android.content.Intent; +import android.os.Bundle; +import android.os.Message; +import android.os.Messenger; +import android.os.Parcelable; +import android.support.v4.app.FragmentActivity; +import org.sufficientlysecure.keychain.R; +import org.sufficientlysecure.keychain.operations.results.InputPendingResult; +import org.sufficientlysecure.keychain.operations.results.OperationResult; +import org.sufficientlysecure.keychain.service.KeychainNewService; +import org.sufficientlysecure.keychain.service.KeychainService; +import org.sufficientlysecure.keychain.service.ServiceProgressHandler; +import org.sufficientlysecure.keychain.service.input.CryptoInputParcel; +import org.sufficientlysecure.keychain.service.input.RequiredInputParcel; +import org.sufficientlysecure.keychain.ui.NfcOperationActivity; +import org.sufficientlysecure.keychain.ui.OrbotRequiredDialogActivity; +import org.sufficientlysecure.keychain.ui.PassphraseDialogActivity; +import org.sufficientlysecure.keychain.ui.dialog.ProgressDialogFragment; + +public abstract class OperationHelper { + public static final int REQUEST_CODE_PASSPHRASE = 0x00008001; + public static final int REQUEST_CODE_NFC = 0x00008002; + public static final int REQUEST_ENABLE_ORBOT = 0x00008004; + + private FragmentActivity mActivity; + + public OperationHelper(FragmentActivity activity) { + mActivity = activity; + } + + private void initiateInputActivity(RequiredInputParcel requiredInput) { + + Log.d("PHILIP", "Initating input " + requiredInput.mType); + switch (requiredInput.mType) { + case NFC_KEYTOCARD: + case NFC_DECRYPT: + case NFC_SIGN: { + Intent intent = new Intent(mActivity, NfcOperationActivity.class); + intent.putExtra(NfcOperationActivity.EXTRA_REQUIRED_INPUT, requiredInput); + mActivity.startActivityForResult(intent, REQUEST_CODE_NFC); + return; + } + + case PASSPHRASE: + case PASSPHRASE_SYMMETRIC: { + Intent intent = new Intent(mActivity, PassphraseDialogActivity.class); + intent.putExtra(PassphraseDialogActivity.EXTRA_REQUIRED_INPUT, requiredInput); + mActivity.startActivityForResult(intent, REQUEST_CODE_PASSPHRASE); + return; + } + + case ENABLE_ORBOT: { + Intent intent = new Intent(mActivity, OrbotRequiredDialogActivity.class); + mActivity.startActivityForResult(intent, REQUEST_ENABLE_ORBOT); + return; + } + } + + throw new RuntimeException("Unhandled pending result!"); + } + + /** + * Attempts the result of an activity started by this helper. Returns true if request code is recognized, + * false otherwise. + * + * @param requestCode + * @param resultCode + * @param data + * @return true if requestCode was recognized, false otherwise + */ + public boolean handleActivityResult(int requestCode, int resultCode, Intent data) { + if (resultCode == Activity.RESULT_CANCELED) { + onCryptoOperationCancelled(); + return true; + } + + switch (requestCode) { + case REQUEST_CODE_PASSPHRASE: { + if (resultCode == Activity.RESULT_OK && data != null) { + CryptoInputParcel cryptoInput = + data.getParcelableExtra(PassphraseDialogActivity.RESULT_CRYPTO_INPUT); + cryptoOperation(cryptoInput); + return true; + } + break; + } + + case REQUEST_CODE_NFC: { + if (resultCode == Activity.RESULT_OK && data != null) { + CryptoInputParcel cryptoInput = + data.getParcelableExtra(NfcOperationActivity.RESULT_DATA); + cryptoOperation(cryptoInput); + return true; + } + break; + } + + case REQUEST_ENABLE_ORBOT: { + if (resultCode == Activity.RESULT_OK && data != null) { + if (data.getBooleanExtra(OrbotRequiredDialogActivity.RESULT_IGNORE_TOR, false)) { + cryptoOperation(new CryptoInputParcel()); + } + return true; + } + break; + } + + default: { + return false; + } + } + return true; + } + + protected void dismissProgress() { + ProgressDialogFragment progressDialogFragment = + (ProgressDialogFragment) mActivity.getSupportFragmentManager().findFragmentByTag("progressDialog"); + + if (progressDialogFragment == null) { + return; + } + + progressDialogFragment.dismissAllowingStateLoss(); + + } + + public abstract T createOperationInput(); + + public void cryptoOperation(CryptoInputParcel cryptoInput) { + + T operationInput = createOperationInput(); + if (operationInput == null) { + return; + } + + // Send all information needed to service to edit key in other thread + Intent intent = new Intent(mActivity, KeychainNewService.class); + + intent.putExtra(KeychainNewService.EXTRA_OPERATION_INPUT, operationInput); + intent.putExtra(KeychainNewService.EXTRA_CRYPTO_INPUT, cryptoInput); + + ServiceProgressHandler saveHandler = new ServiceProgressHandler(mActivity) { + @Override + public void handleMessage(Message message) { + // handle messages by standard KeychainIntentServiceHandler first + super.handleMessage(message); + + if (message.arg1 == MessageStatus.OKAY.ordinal()) { + + // get returned data bundle + Bundle returnData = message.getData(); + if (returnData == null) { + return; + } + + final OperationResult result = + returnData.getParcelable(OperationResult.EXTRA_RESULT); + + onHandleResult(result); + } + } + }; + + // Create a new Messenger for the communication back + Messenger messenger = new Messenger(saveHandler); + intent.putExtra(KeychainService.EXTRA_MESSENGER, messenger); + + saveHandler.showProgressDialog( + mActivity.getString(R.string.progress_building_key), + ProgressDialog.STYLE_HORIZONTAL, false); + + mActivity.startService(intent); + + } + + public void cryptoOperation() { + cryptoOperation(new CryptoInputParcel()); + } + + protected void onCryptoOperationResult(S result) { + Log.d("PHILIP", "cryptoResult " + result.success()); + if (result.success()) { + onCryptoOperationSuccess(result); + } else { + onCryptoOperationError(result); + } + } + + abstract protected void onCryptoOperationSuccess(S result); + + protected void onCryptoOperationError(S result) { + result.createNotify(mActivity).show(); + } + + protected void onCryptoOperationCancelled() { + } + + public void onHandleResult(OperationResult result) { + Log.d("PHILIP", "Handling result in OperationHelper"); + + if (result instanceof InputPendingResult) { + Log.d("PHILIP", "is pending result"); + InputPendingResult pendingResult = (InputPendingResult) result; + if (pendingResult.isPending()) { + + Log.d("PHILIP", "Is pending"); + RequiredInputParcel requiredInput = pendingResult.getRequiredInputParcel(); + initiateInputActivity(requiredInput); + return; + } + } + + dismissProgress(); + + try { + // noinspection unchecked, because type erasure :( + onCryptoOperationResult((S) result); + } catch (ClassCastException e) { + throw new AssertionError("bad return class (" + + result.getClass().getSimpleName() + "), this is a programming error!"); + } + + } +}