aboutsummaryrefslogtreecommitdiffstats
path: root/OpenKeychain/src/main
diff options
context:
space:
mode:
Diffstat (limited to 'OpenKeychain/src/main')
-rw-r--r--OpenKeychain/src/main/AndroidManifest.xml1
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/BaseOperation.java17
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/CertifyOperation.java21
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/DeleteOperation.java17
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/EditKeyOperation.java17
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/PromoteKeyOperation.java17
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/SignEncryptOperation.java20
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainContract.java1
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainProvider.java10
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/AccountSettingsFragment.java6
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/SelectSignKeyIdActivity.java4
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentService.java93
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentServiceHandler.java35
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CertifyKeyFragment.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ConsolidateDialogActivity.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CreateKeyFinalFragment.java4
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptFilesFragment.java13
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptTextFragment.java5
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EditKeyFragment.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptActivity.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesActivity.java39
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesFragment.java7
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysActivity.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysProxyActivity.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/KeyListFragment.java7
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/SafeSlingerActivity.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/UploadKeyActivity.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyActivity.java13
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyFragment.java46
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyTrustFragment.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteFileDialogFragment.java106
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteKeyDialogFragment.java2
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/CertifyKeySpinner.java4
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/KeySpinner.java43
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/SignKeySpinner.java4
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ContactHelper.java296
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ExportHelper.java2
-rw-r--r--OpenKeychain/src/main/res/layout/keyspinner_item.xml4
-rw-r--r--OpenKeychain/src/main/res/values-cs/strings.xml6
-rw-r--r--OpenKeychain/src/main/res/values-de/strings.xml4
-rw-r--r--OpenKeychain/src/main/res/values-es/strings.xml4
-rw-r--r--OpenKeychain/src/main/res/values-et/strings.xml8
-rw-r--r--OpenKeychain/src/main/res/values-eu/strings.xml2
-rw-r--r--OpenKeychain/src/main/res/values-fi/strings.xml8
-rw-r--r--OpenKeychain/src/main/res/values-fr/strings.xml4
-rw-r--r--OpenKeychain/src/main/res/values-it/strings.xml6
-rw-r--r--OpenKeychain/src/main/res/values-ja/strings.xml5
-rw-r--r--OpenKeychain/src/main/res/values-nl/strings.xml8
-rw-r--r--OpenKeychain/src/main/res/values-pl/strings.xml6
-rw-r--r--OpenKeychain/src/main/res/values-ru/strings.xml4
-rw-r--r--OpenKeychain/src/main/res/values-sl/strings.xml6
-rw-r--r--OpenKeychain/src/main/res/values-sr/strings.xml8
-rw-r--r--OpenKeychain/src/main/res/values-sv/strings.xml4
-rw-r--r--OpenKeychain/src/main/res/values-tr/strings.xml6
-rw-r--r--OpenKeychain/src/main/res/values-uk/strings.xml6
-rw-r--r--OpenKeychain/src/main/res/values-zh-rTW/strings.xml6
-rw-r--r--OpenKeychain/src/main/res/values-zh/strings.xml4
-rw-r--r--OpenKeychain/src/main/res/values/strings.xml8
58 files changed, 739 insertions, 246 deletions
diff --git a/OpenKeychain/src/main/AndroidManifest.xml b/OpenKeychain/src/main/AndroidManifest.xml
index 5d3a106de..0e7baf039 100644
--- a/OpenKeychain/src/main/AndroidManifest.xml
+++ b/OpenKeychain/src/main/AndroidManifest.xml
@@ -65,6 +65,7 @@
<uses-permission android:name="android.permission.READ_CONTACTS" />
<uses-permission android:name="android.permission.WRITE_CONTACTS" />
<uses-permission android:name="android.permission.READ_PROFILE" />
+ <uses-permission android:name="android.permission.WRITE_PROFILE" />
<!-- android:allowBackup="false": Don't allow backup over adb backup or other apps! -->
<application
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/BaseOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/BaseOperation.java
index e796bdc91..40dcbd78d 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/BaseOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/BaseOperation.java
@@ -1,3 +1,20 @@
+/*
+ * Copyright (C) 2014-2015 Vincent Breitmoser <v.breitmoser@mugenguild.com>
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
package org.sufficientlysecure.keychain.operations;
import android.content.Context;
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/CertifyOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/CertifyOperation.java
index 2e9551826..ebf0dc70b 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/CertifyOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/CertifyOperation.java
@@ -1,3 +1,20 @@
+/*
+ * Copyright (C) 2014-2015 Vincent Breitmoser <v.breitmoser@mugenguild.com>
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
package org.sufficientlysecure.keychain.operations;
import android.content.Context;
@@ -20,6 +37,7 @@ import org.sufficientlysecure.keychain.provider.ProviderHelper;
import org.sufficientlysecure.keychain.provider.ProviderHelper.NotFoundException;
import org.sufficientlysecure.keychain.service.CertifyActionsParcel;
import org.sufficientlysecure.keychain.service.CertifyActionsParcel.CertifyAction;
+import org.sufficientlysecure.keychain.service.ContactSyncAdapterService;
import org.sufficientlysecure.keychain.ui.util.KeyFormattingUtils;
import org.sufficientlysecure.keychain.util.Log;
@@ -191,6 +209,9 @@ public class CertifyOperation extends BaseOperation {
}
log.add(LogType.MSG_CRT_SUCCESS, 0);
+ //since only verified keys are synced to contacts, we need to initiate a sync now
+ ContactSyncAdapterService.requestSync();
+
return new CertifyResult(CertifyResult.RESULT_OK, log, certifyOk, certifyError, uploadOk, uploadError);
}
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/DeleteOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/DeleteOperation.java
index 124dd1aaf..5ef04ab05 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/DeleteOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/DeleteOperation.java
@@ -1,3 +1,20 @@
+/*
+ * Copyright (C) 2014-2015 Vincent Breitmoser <v.breitmoser@mugenguild.com>
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
package org.sufficientlysecure.keychain.operations;
import android.content.Context;
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/EditKeyOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/EditKeyOperation.java
index 7f14b08d9..bcd842dd0 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/EditKeyOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/EditKeyOperation.java
@@ -1,3 +1,20 @@
+/*
+ * Copyright (C) 2014-2015 Vincent Breitmoser <v.breitmoser@mugenguild.com>
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
package org.sufficientlysecure.keychain.operations;
import android.content.Context;
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/PromoteKeyOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/PromoteKeyOperation.java
index 783b32477..fd86d4b92 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/PromoteKeyOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/PromoteKeyOperation.java
@@ -1,3 +1,20 @@
+/*
+ * Copyright (C) 2014-2015 Vincent Breitmoser <v.breitmoser@mugenguild.com>
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
package org.sufficientlysecure.keychain.operations;
import android.content.Context;
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/SignEncryptOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/SignEncryptOperation.java
index e98f6b150..b5552a40d 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/SignEncryptOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/operations/SignEncryptOperation.java
@@ -1,3 +1,20 @@
+/*
+ * Copyright (C) 2014-2015 Vincent Breitmoser <v.breitmoser@mugenguild.com>
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
package org.sufficientlysecure.keychain.operations;
import android.content.Context;
@@ -48,6 +65,7 @@ public class SignEncryptOperation extends BaseOperation {
byte[] inputBytes = input.getBytes();
byte[] outputBytes = null;
+ int total = inputBytes != null ? 1 : inputUris.size(), count = 0;
ArrayList<PgpSignEncryptResult> results = new ArrayList<>();
do {
@@ -104,7 +122,7 @@ public class SignEncryptOperation extends BaseOperation {
}
PgpSignEncryptOperation op = new PgpSignEncryptOperation(mContext, mProviderHelper,
- new ProgressScaler(), mCancelled);
+ new ProgressScaler(mProgressable, 100 * count / total, 100 * ++count / total, 100), mCancelled);
PgpSignEncryptResult result = op.execute(input, inputData, outStream);
results.add(result);
log.add(result, 2);
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainContract.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainContract.java
index 5856589c4..6af5f4217 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainContract.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainContract.java
@@ -123,6 +123,7 @@ public class KeychainContract {
public static final String HAS_SIGN = "has_sign";
public static final String HAS_CERTIFY = "has_certify";
public static final String HAS_AUTHENTICATE = "has_authenticate";
+ public static final String HAS_DUPLICATE_USER_ID = "has_duplicate_user_id";
public static final String PUBKEY_DATA = "pubkey_data";
public static final String PRIVKEY_DATA = "privkey_data";
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainProvider.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainProvider.java
index 4ccfc3cd9..1351e0cbc 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainProvider.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/provider/KeychainProvider.java
@@ -273,7 +273,15 @@ public class KeychainProvider extends ContentProvider {
projectionMap.put(KeyRings.EXPIRY, Tables.KEYS + "." + Keys.EXPIRY);
projectionMap.put(KeyRings.ALGORITHM, Tables.KEYS + "." + Keys.ALGORITHM);
projectionMap.put(KeyRings.FINGERPRINT, Tables.KEYS + "." + Keys.FINGERPRINT);
- projectionMap.put(KeyRings.USER_ID, UserPackets.USER_ID);
+ projectionMap.put(KeyRings.USER_ID, Tables.USER_PACKETS + "." + UserPackets.USER_ID);
+ projectionMap.put(KeyRings.HAS_DUPLICATE_USER_ID,
+ "(SELECT COUNT (*) FROM " + Tables.USER_PACKETS + " AS dups"
+ + " WHERE dups." + UserPackets.MASTER_KEY_ID
+ + " != " + Tables.KEYS + "." + Keys.MASTER_KEY_ID
+ + " AND dups." + UserPackets.RANK + " = 0"
+ + " AND dups." + UserPackets.USER_ID
+ + " = "+ Tables.USER_PACKETS + "." + UserPackets.USER_ID
+ + ") AS " + KeyRings.HAS_DUPLICATE_USER_ID);
projectionMap.put(KeyRings.VERIFIED, KeyRings.VERIFIED);
projectionMap.put(KeyRings.PUBKEY_DATA,
Tables.KEY_RINGS_PUBLIC + "." + KeyRingData.KEY_RING_DATA
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 940ae27d0..4bb64bcaa 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
@@ -28,8 +28,8 @@ import android.widget.TextView;
import org.sufficientlysecure.keychain.Constants;
import org.sufficientlysecure.keychain.R;
+import org.sufficientlysecure.keychain.operations.results.EditKeyResult;
import org.sufficientlysecure.keychain.operations.results.OperationResult;
-import org.sufficientlysecure.keychain.operations.results.SaveKeyringResult;
import org.sufficientlysecure.keychain.pgp.KeyRing;
import org.sufficientlysecure.keychain.remote.AccountSettings;
import org.sufficientlysecure.keychain.ui.CreateKeyActivity;
@@ -106,8 +106,8 @@ public class AccountSettingsFragment extends Fragment {
case REQUEST_CODE_CREATE_KEY: {
if (resultCode == Activity.RESULT_OK) {
if (data != null && data.hasExtra(OperationResult.EXTRA_RESULT)) {
- SaveKeyringResult result = data.getParcelableExtra(OperationResult.EXTRA_RESULT);
- mSelectKeySpinner.setSelectedKeyId(result.mRingMasterKeyId);
+ EditKeyResult result = data.getParcelableExtra(OperationResult.EXTRA_RESULT);
+ mSelectKeySpinner.setSelectedKeyId(result.mMasterKeyId);
} else {
Log.e(Constants.TAG, "missing result!");
}
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/SelectSignKeyIdActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/SelectSignKeyIdActivity.java
index 8578bb384..5ec47f4c9 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/SelectSignKeyIdActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/remote/ui/SelectSignKeyIdActivity.java
@@ -127,9 +127,9 @@ public class SelectSignKeyIdActivity extends BaseActivity {
case REQUEST_CODE_CREATE_KEY: {
if (resultCode == Activity.RESULT_OK) {
if (data != null && data.hasExtra(OperationResult.EXTRA_RESULT)) {
-// SaveKeyringResult result = data.getParcelableExtra(OperationResult.EXTRA_RESULT);
// TODO: select?
-// mSelectKeySpinner.setSelectedKeyId(result.mRingMasterKeyId);
+// EditKeyResult result = data.getParcelableExtra(OperationResult.EXTRA_RESULT);
+// mSelectKeySpinner.setSelectedKeyId(result.mMasterKeyId);
} else {
Log.e(Constants.TAG, "missing result!");
}
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentService.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentService.java
index d95701458..bf6a62782 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentService.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentService.java
@@ -60,6 +60,7 @@ import org.sufficientlysecure.keychain.pgp.SignEncryptParcel;
import org.sufficientlysecure.keychain.pgp.exception.PgpGeneralException;
import org.sufficientlysecure.keychain.pgp.exception.PgpGeneralMsgIdException;
import org.sufficientlysecure.keychain.provider.ProviderHelper;
+import org.sufficientlysecure.keychain.service.KeychainIntentServiceHandler.MessageStatus;
import org.sufficientlysecure.keychain.util.FileHelper;
import org.sufficientlysecure.keychain.util.InputData;
import org.sufficientlysecure.keychain.util.Log;
@@ -126,8 +127,21 @@ public class KeychainIntentService extends IntentService implements Progressable
public static final String SOURCE = "source";
// possible targets:
- public static final int IO_BYTES = 1;
- public static final int IO_URI = 2;
+ public static enum IOType {
+ UNKNOWN,
+ BYTES,
+ URI;
+
+ private static final IOType[] values = values();
+
+ public static IOType fromInt(int n) {
+ if(n < 0 || n >= values.length) {
+ return UNKNOWN;
+ } else {
+ return values[n];
+ }
+ }
+ }
// encrypt
public static final String ENCRYPT_DECRYPT_INPUT_URI = "input_uri";
@@ -244,7 +258,7 @@ public class KeychainIntentService extends IntentService implements Progressable
CertifyResult result = op.certify(parcel, keyServerUri);
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
}
@@ -259,7 +273,7 @@ public class KeychainIntentService extends IntentService implements Progressable
}
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
}
@@ -288,7 +302,7 @@ public class KeychainIntentService extends IntentService implements Progressable
DecryptVerifyResult decryptVerifyResult = builder.build().execute();
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, decryptVerifyResult);
+ sendMessageToHandler(MessageStatus.OKAY, decryptVerifyResult);
} catch (Exception e) {
sendErrorToHandler(e);
}
@@ -349,7 +363,7 @@ public class KeychainIntentService extends IntentService implements Progressable
}
// kind of awkward, but this whole class wants to pull bytes out of “data”
- data.putInt(KeychainIntentService.TARGET, KeychainIntentService.IO_BYTES);
+ data.putInt(KeychainIntentService.TARGET, IOType.BYTES.ordinal());
data.putByteArray(KeychainIntentService.DECRYPT_CIPHERTEXT_BYTES, messageBytes);
InputData inputData = createDecryptInputData(data);
@@ -386,7 +400,7 @@ public class KeychainIntentService extends IntentService implements Progressable
resultData.putString(KeychainIntentServiceHandler.KEYBASE_PROOF_URL, prover.getProofUrl());
resultData.putString(KeychainIntentServiceHandler.KEYBASE_PRESENCE_URL, prover.getPresenceUrl());
resultData.putString(KeychainIntentServiceHandler.KEYBASE_PRESENCE_LABEL, prover.getPresenceLabel());
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, resultData);
+ sendMessageToHandler(MessageStatus.OKAY, resultData);
} catch (Exception e) {
sendErrorToHandler(e);
}
@@ -429,7 +443,7 @@ public class KeychainIntentService extends IntentService implements Progressable
Log.logDebugBundle(resultData, "resultData");
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, resultData);
+ sendMessageToHandler(MessageStatus.OKAY, resultData);
} catch (Exception e) {
sendErrorToHandler(e);
}
@@ -447,7 +461,7 @@ public class KeychainIntentService extends IntentService implements Progressable
DeleteResult result = op.execute(masterKeyIds, isSecret);
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
}
@@ -462,7 +476,7 @@ public class KeychainIntentService extends IntentService implements Progressable
EditKeyResult result = op.execute(saveParcel, passphrase);
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
}
@@ -476,7 +490,7 @@ public class KeychainIntentService extends IntentService implements Progressable
PromoteKeyResult result = op.execute(keyRingId);
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
}
@@ -500,7 +514,7 @@ public class KeychainIntentService extends IntentService implements Progressable
}
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
}
@@ -521,7 +535,7 @@ public class KeychainIntentService extends IntentService implements Progressable
: importExportOperation.importKeyRings(cache, keyServer);
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
@@ -537,7 +551,7 @@ public class KeychainIntentService extends IntentService implements Progressable
SignEncryptResult result = op.execute(inputParcel);
// Result
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, result);
+ sendMessageToHandler(MessageStatus.OKAY, result);
break;
}
@@ -560,7 +574,7 @@ public class KeychainIntentService extends IntentService implements Progressable
throw new PgpGeneralException("Unable to export key to selected server");
}
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY);
+ sendMessageToHandler(MessageStatus.OKAY);
} catch (Exception e) {
sendErrorToHandler(e);
}
@@ -582,7 +596,7 @@ public class KeychainIntentService extends IntentService implements Progressable
private void sendProofError(String msg) {
Bundle bundle = new Bundle();
bundle.putString(KeychainIntentServiceHandler.DATA_ERROR, msg);
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_OKAY, bundle);
+ sendMessageToHandler(MessageStatus.OKAY, bundle);
}
private void sendErrorToHandler(Exception e) {
@@ -599,14 +613,14 @@ public class KeychainIntentService extends IntentService implements Progressable
Bundle data = new Bundle();
data.putString(KeychainIntentServiceHandler.DATA_ERROR, message);
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_EXCEPTION, null, data);
+ sendMessageToHandler(MessageStatus.EXCEPTION, null, data);
}
- private void sendMessageToHandler(Integer arg1, Integer arg2, Bundle data) {
+ private void sendMessageToHandler(MessageStatus status, Integer arg2, Bundle data) {
Message msg = Message.obtain();
assert msg != null;
- msg.arg1 = arg1;
+ msg.arg1 = status.ordinal();
if (arg2 != null) {
msg.arg2 = arg2;
}
@@ -623,18 +637,18 @@ public class KeychainIntentService extends IntentService implements Progressable
}
}
- private void sendMessageToHandler(Integer arg1, OperationResult data) {
+ private void sendMessageToHandler(MessageStatus status, OperationResult data) {
Bundle bundle = new Bundle();
bundle.putParcelable(OperationResult.EXTRA_RESULT, data);
- sendMessageToHandler(arg1, null, bundle);
+ sendMessageToHandler(status, null, bundle);
}
- private void sendMessageToHandler(Integer arg1, Bundle data) {
- sendMessageToHandler(arg1, null, data);
+ private void sendMessageToHandler(MessageStatus status, Bundle data) {
+ sendMessageToHandler(status, null, data);
}
- private void sendMessageToHandler(Integer arg1) {
- sendMessageToHandler(arg1, null, null);
+ private void sendMessageToHandler(MessageStatus status) {
+ sendMessageToHandler(status, null, null);
}
/**
@@ -651,7 +665,7 @@ public class KeychainIntentService extends IntentService implements Progressable
data.putInt(KeychainIntentServiceHandler.DATA_PROGRESS, progress);
data.putInt(KeychainIntentServiceHandler.DATA_PROGRESS_MAX, max);
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_UPDATE_PROGRESS, null, data);
+ sendMessageToHandler(MessageStatus.UPDATE_PROGRESS, null, data);
}
public void setProgress(int resourceId, int progress, int max) {
@@ -664,7 +678,7 @@ public class KeychainIntentService extends IntentService implements Progressable
@Override
public void setPreventCancel() {
- sendMessageToHandler(KeychainIntentServiceHandler.MESSAGE_PREVENT_CANCEL);
+ sendMessageToHandler(MessageStatus.PREVENT_CANCEL);
}
private InputData createDecryptInputData(Bundle data) throws IOException, PgpGeneralException {
@@ -673,35 +687,37 @@ public class KeychainIntentService extends IntentService implements Progressable
private InputData createCryptInputData(Bundle data, String bytesName) throws PgpGeneralException, IOException {
int source = data.get(SOURCE) != null ? data.getInt(SOURCE) : data.getInt(TARGET);
- switch (source) {
- case IO_BYTES: /* encrypting bytes directly */
+ IOType type = IOType.fromInt(source);
+ switch (type) {
+ case BYTES: /* encrypting bytes directly */
byte[] bytes = data.getByteArray(bytesName);
return new InputData(new ByteArrayInputStream(bytes), bytes.length);
- case IO_URI: /* encrypting content uri */
+ case URI: /* encrypting content uri */
Uri providerUri = data.getParcelable(ENCRYPT_DECRYPT_INPUT_URI);
// InputStream
return new InputData(getContentResolver().openInputStream(providerUri), FileHelper.getFileSize(this, providerUri, 0));
default:
- throw new PgpGeneralException("No target choosen!");
+ throw new PgpGeneralException("No target chosen!");
}
}
private OutputStream createCryptOutputStream(Bundle data) throws PgpGeneralException, FileNotFoundException {
int target = data.getInt(TARGET);
- switch (target) {
- case IO_BYTES:
+ IOType type = IOType.fromInt(target);
+ switch (type) {
+ case BYTES:
return new ByteArrayOutputStream();
- case IO_URI:
+ case URI:
Uri providerUri = data.getParcelable(ENCRYPT_DECRYPT_OUTPUT_URI);
return getContentResolver().openOutputStream(providerUri);
default:
- throw new PgpGeneralException("No target choosen!");
+ throw new PgpGeneralException("No target chosen!");
}
}
@@ -711,12 +727,13 @@ public class KeychainIntentService extends IntentService implements Progressable
private void finalizeCryptOutputStream(Bundle data, Bundle resultData, OutputStream outStream, String bytesName) {
int target = data.getInt(TARGET);
- switch (target) {
- case IO_BYTES:
+ IOType type = IOType.fromInt(target);
+ switch (type) {
+ case BYTES:
byte output[] = ((ByteArrayOutputStream) outStream).toByteArray();
resultData.putByteArray(bytesName, output);
break;
- case IO_URI:
+ case URI:
// nothing, output was written, just send okay and verification bundle
break;
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentServiceHandler.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentServiceHandler.java
index 635fe86f1..bd047518d 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentServiceHandler.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/service/KeychainIntentServiceHandler.java
@@ -32,11 +32,25 @@ import org.sufficientlysecure.keychain.util.Log;
public class KeychainIntentServiceHandler extends Handler {
- // possible messages send from this service to handler on ui
- public static final int MESSAGE_OKAY = 1;
- public static final int MESSAGE_EXCEPTION = 2;
- public static final int MESSAGE_UPDATE_PROGRESS = 3;
- public static final int MESSAGE_PREVENT_CANCEL = 4;
+ // possible messages sent from this service to handler on ui
+ public static enum MessageStatus{
+ UNKNOWN,
+ OKAY,
+ EXCEPTION,
+ UPDATE_PROGRESS,
+ PREVENT_CANCEL;
+
+ private static final MessageStatus[] values = values();
+
+ public static MessageStatus fromInt(int n)
+ {
+ if(n < 0 || n >= values.length) {
+ return UNKNOWN;
+ } else {
+ return values[n];
+ }
+ }
+ }
// possible data keys for messages
public static final String DATA_ERROR = "error";
@@ -103,13 +117,14 @@ public class KeychainIntentServiceHandler extends Handler {
return;
}
- switch (message.arg1) {
- case MESSAGE_OKAY:
+ MessageStatus status = MessageStatus.fromInt(message.arg1);
+ switch (status) {
+ case OKAY:
mProgressDialogFragment.dismissAllowingStateLoss();
break;
- case MESSAGE_EXCEPTION:
+ case EXCEPTION:
mProgressDialogFragment.dismissAllowingStateLoss();
// show error from service
@@ -121,7 +136,7 @@ public class KeychainIntentServiceHandler extends Handler {
break;
- case MESSAGE_UPDATE_PROGRESS:
+ case UPDATE_PROGRESS:
if (data.containsKey(DATA_PROGRESS) && data.containsKey(DATA_PROGRESS_MAX)) {
// update progress from service
@@ -139,7 +154,7 @@ public class KeychainIntentServiceHandler extends Handler {
break;
- case MESSAGE_PREVENT_CANCEL:
+ case PREVENT_CANCEL:
mProgressDialogFragment.setPreventCancel(true);
break;
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CertifyKeyFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CertifyKeyFragment.java
index e1467ec61..1e1bd32c1 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CertifyKeyFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CertifyKeyFragment.java
@@ -395,7 +395,7 @@ public class CertifyKeyFragment extends LoaderFragment
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
Bundle data = message.getData();
CertifyResult result = data.getParcelable(CertifyResult.EXTRA_RESULT);
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ConsolidateDialogActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ConsolidateDialogActivity.java
index f0ef8b9ef..c55aad1f9 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ConsolidateDialogActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ConsolidateDialogActivity.java
@@ -57,7 +57,7 @@ public class ConsolidateDialogActivity extends FragmentActivity {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
/* don't care about the results (for now?)
// get returned data bundle
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CreateKeyFinalFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CreateKeyFinalFragment.java
index 4853c61c5..ae42c891d 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CreateKeyFinalFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/CreateKeyFinalFragment.java
@@ -214,7 +214,7 @@ public class CreateKeyFinalFragment extends Fragment {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
if (returnData == null) {
@@ -284,7 +284,7 @@ public class CreateKeyFinalFragment extends Fragment {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// TODO: upload operation needs a result!
// TODO: then combine these results
//if (result.getResult() == OperationResultParcel.RESULT_OK) {
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptFilesFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptFilesFragment.java
index 5606523be..c808557a6 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptFilesFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptFilesFragment.java
@@ -37,6 +37,7 @@ import org.sufficientlysecure.keychain.Constants;
import org.sufficientlysecure.keychain.R;
import org.sufficientlysecure.keychain.operations.results.DecryptVerifyResult;
import org.sufficientlysecure.keychain.service.KeychainIntentService;
+import org.sufficientlysecure.keychain.service.KeychainIntentService.IOType;
import org.sufficientlysecure.keychain.service.KeychainIntentServiceHandler;
import org.sufficientlysecure.keychain.ui.dialog.DeleteFileDialogFragment;
import org.sufficientlysecure.keychain.ui.util.Notify;
@@ -182,10 +183,10 @@ public class DecryptFilesFragment extends DecryptFragment {
// data
Log.d(Constants.TAG, "mInputUri=" + mInputUri + ", mOutputUri=" + mOutputUri);
- data.putInt(KeychainIntentService.SOURCE, KeychainIntentService.IO_URI);
+ data.putInt(KeychainIntentService.SOURCE, IOType.URI.ordinal());
data.putParcelable(KeychainIntentService.ENCRYPT_DECRYPT_INPUT_URI, mInputUri);
- data.putInt(KeychainIntentService.TARGET, KeychainIntentService.IO_URI);
+ data.putInt(KeychainIntentService.TARGET, IOType.URI.ordinal());
data.putParcelable(KeychainIntentService.ENCRYPT_DECRYPT_OUTPUT_URI, mOutputUri);
data.putString(KeychainIntentService.DECRYPT_PASSPHRASE, mPassphrase);
@@ -200,7 +201,7 @@ public class DecryptFilesFragment extends DecryptFragment {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
@@ -256,10 +257,10 @@ public class DecryptFilesFragment extends DecryptFragment {
// data
Log.d(Constants.TAG, "mInputUri=" + mInputUri + ", mOutputUri=" + mOutputUri);
- data.putInt(KeychainIntentService.SOURCE, KeychainIntentService.IO_URI);
+ data.putInt(KeychainIntentService.SOURCE, IOType.URI.ordinal());
data.putParcelable(KeychainIntentService.ENCRYPT_DECRYPT_INPUT_URI, mInputUri);
- data.putInt(KeychainIntentService.TARGET, KeychainIntentService.IO_URI);
+ data.putInt(KeychainIntentService.TARGET, IOType.URI.ordinal());
data.putParcelable(KeychainIntentService.ENCRYPT_DECRYPT_OUTPUT_URI, mOutputUri);
data.putString(KeychainIntentService.DECRYPT_PASSPHRASE, mPassphrase);
@@ -274,7 +275,7 @@ public class DecryptFilesFragment extends DecryptFragment {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptTextFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptTextFragment.java
index a15b23c06..1b34f6bf0 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptTextFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/DecryptTextFragment.java
@@ -36,6 +36,7 @@ import org.sufficientlysecure.keychain.R;
import org.sufficientlysecure.keychain.compatibility.ClipboardReflection;
import org.sufficientlysecure.keychain.operations.results.DecryptVerifyResult;
import org.sufficientlysecure.keychain.service.KeychainIntentService;
+import org.sufficientlysecure.keychain.service.KeychainIntentService.IOType;
import org.sufficientlysecure.keychain.service.KeychainIntentServiceHandler;
import org.sufficientlysecure.keychain.ui.util.Notify;
import org.sufficientlysecure.keychain.util.Log;
@@ -158,7 +159,7 @@ public class DecryptTextFragment extends DecryptFragment {
intent.setAction(KeychainIntentService.ACTION_DECRYPT_VERIFY);
// data
- data.putInt(KeychainIntentService.TARGET, KeychainIntentService.IO_BYTES);
+ data.putInt(KeychainIntentService.TARGET, IOType.BYTES.ordinal());
data.putByteArray(KeychainIntentService.DECRYPT_CIPHERTEXT_BYTES, mCiphertext.getBytes());
data.putString(KeychainIntentService.DECRYPT_PASSPHRASE, mPassphrase);
data.putByteArray(KeychainIntentService.DECRYPT_NFC_DECRYPTED_SESSION_KEY, mNfcDecryptedSessionKey);
@@ -172,7 +173,7 @@ public class DecryptTextFragment extends DecryptFragment {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
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 1e9a90fc8..8b9323f19 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EditKeyFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EditKeyFragment.java
@@ -605,7 +605,7 @@ public class EditKeyFragment extends LoaderFragment implements
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptActivity.java
index ed5920cde..35dfcb87c 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptActivity.java
@@ -128,7 +128,7 @@ public abstract class EncryptActivity extends BaseActivity {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
SignEncryptResult result =
message.getData().getParcelable(SignEncryptResult.EXTRA_RESULT);
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesActivity.java
index d95b5cda3..b862d5b11 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesActivity.java
@@ -36,7 +36,6 @@ import org.sufficientlysecure.keychain.pgp.SignEncryptParcel;
import org.sufficientlysecure.keychain.ui.dialog.DeleteFileDialogFragment;
import org.sufficientlysecure.keychain.ui.util.Notify;
import org.sufficientlysecure.keychain.util.Log;
-import org.sufficientlysecure.keychain.util.Preferences;
import org.sufficientlysecure.keychain.util.ShareHelper;
import java.util.ArrayList;
@@ -177,22 +176,36 @@ public class EncryptFilesActivity extends EncryptActivity implements EncryptActi
}
@Override
- public void onEncryptSuccess(SignEncryptResult result) {
+ public void onEncryptSuccess(final SignEncryptResult result) {
if (mDeleteAfterEncrypt) {
- for (Uri inputUri : mInputUris) {
- DeleteFileDialogFragment deleteFileDialog = DeleteFileDialogFragment.newInstance(inputUri);
- deleteFileDialog.show(getSupportFragmentManager(), "deleteDialog");
- }
+ final Uri[] inputUris = mInputUris.toArray(new Uri[mInputUris.size()]);
+ DeleteFileDialogFragment deleteFileDialog = DeleteFileDialogFragment.newInstance(inputUris);
+ deleteFileDialog.setOnDeletedListener(new DeleteFileDialogFragment.OnDeletedListener() {
+
+ @Override
+ public void onDeleted() {
+ if (mShareAfterEncrypt) {
+ // Share encrypted message/file
+ startActivity(sendWithChooserExcludingEncrypt());
+ } else {
+ // Save encrypted file
+ result.createNotify(EncryptFilesActivity.this).show();
+ }
+ }
+
+ });
+ deleteFileDialog.show(getSupportFragmentManager(), "deleteDialog");
+
mInputUris.clear();
notifyUpdate();
- }
-
- if (mShareAfterEncrypt) {
- // Share encrypted message/file
- startActivity(sendWithChooserExcludingEncrypt());
} else {
- // Save encrypted file
- result.createNotify(EncryptFilesActivity.this).show();
+ if (mShareAfterEncrypt) {
+ // Share encrypted message/file
+ startActivity(sendWithChooserExcludingEncrypt());
+ } else {
+ // Save encrypted file
+ result.createNotify(EncryptFilesActivity.this).show();
+ }
}
}
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 ace58b165..48737d223 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/EncryptFilesFragment.java
@@ -114,6 +114,13 @@ public class EncryptFilesFragment extends Fragment implements EncryptActivityInt
return;
}
+ if (mEncryptInterface.getInputUris().contains(inputUri)) {
+ Notify.showNotify(getActivity(),
+ getActivity().getString(R.string.error_file_added_already, FileHelper.getFilename(getActivity(), inputUri)),
+ Notify.Style.ERROR);
+ return;
+ }
+
mEncryptInterface.getInputUris().add(inputUri);
mEncryptInterface.notifyUpdate();
mSelectedFiles.requestFocus();
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 71f6fd4bf..d51e2c7fc 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysActivity.java
@@ -302,7 +302,7 @@ public class ImportKeysActivity extends BaseActivity {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
if (returnData == null) {
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysProxyActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysProxyActivity.java
index 948da94d8..cc8b47971 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysProxyActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ImportKeysProxyActivity.java
@@ -222,7 +222,7 @@ public class ImportKeysProxyActivity extends FragmentActivity {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
if (returnData == null) {
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/KeyListFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/KeyListFragment.java
index 43d893fa6..8c34efba2 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/KeyListFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/KeyListFragment.java
@@ -270,7 +270,8 @@ public class KeyListFragment extends LoaderFragment
KeyRings.IS_REVOKED,
KeyRings.IS_EXPIRED,
KeyRings.VERIFIED,
- KeyRings.HAS_ANY_SECRET
+ KeyRings.HAS_ANY_SECRET,
+ KeyRings.HAS_DUPLICATE_USER_ID,
};
static final int INDEX_MASTER_KEY_ID = 1;
@@ -279,6 +280,7 @@ public class KeyListFragment extends LoaderFragment
static final int INDEX_IS_EXPIRED = 4;
static final int INDEX_VERIFIED = 5;
static final int INDEX_HAS_ANY_SECRET = 6;
+ static final int INDEX_HAS_DUPLICATE_USER_ID = 7;
static final String ORDER =
KeyRings.HAS_ANY_SECRET + " DESC, UPPER(" + KeyRings.USER_ID + ") ASC";
@@ -552,7 +554,7 @@ public class KeyListFragment extends LoaderFragment
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
if (returnData == null) {
@@ -707,6 +709,7 @@ public class KeyListFragment extends LoaderFragment
boolean isRevoked = cursor.getInt(INDEX_IS_REVOKED) > 0;
boolean isExpired = cursor.getInt(INDEX_IS_EXPIRED) != 0;
boolean isVerified = cursor.getInt(INDEX_VERIFIED) > 0;
+ boolean hasDuplicate = cursor.getInt(INDEX_HAS_DUPLICATE_USER_ID) == 1;
h.mMasterKeyId = masterKeyId;
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/SafeSlingerActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/SafeSlingerActivity.java
index d1df2906d..d0cea5f05 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/SafeSlingerActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/SafeSlingerActivity.java
@@ -132,7 +132,7 @@ public class SafeSlingerActivity extends BaseActivity {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
if (returnData == null) {
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/UploadKeyActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/UploadKeyActivity.java
index e19793fd5..4fb2074a5 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/UploadKeyActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/UploadKeyActivity.java
@@ -113,7 +113,7 @@ public class UploadKeyActivity extends BaseActivity {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
Toast.makeText(UploadKeyActivity.this, R.string.msg_crt_upload_success,
Toast.LENGTH_SHORT).show();
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyActivity.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyActivity.java
index c94b29bac..b25f6bbf2 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyActivity.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyActivity.java
@@ -25,6 +25,7 @@ import android.annotation.TargetApi;
import android.app.Activity;
import android.app.ActivityOptions;
import android.content.Intent;
+import android.content.pm.PackageManager;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.net.Uri;
@@ -72,6 +73,7 @@ import org.sufficientlysecure.keychain.provider.KeychainContract;
import org.sufficientlysecure.keychain.provider.ProviderHelper;
import org.sufficientlysecure.keychain.service.KeychainIntentService;
import org.sufficientlysecure.keychain.service.KeychainIntentServiceHandler;
+import org.sufficientlysecure.keychain.service.KeychainIntentServiceHandler.MessageStatus;
import org.sufficientlysecure.keychain.ui.util.FormattingUtils;
import org.sufficientlysecure.keychain.ui.util.KeyFormattingUtils;
import org.sufficientlysecure.keychain.ui.util.KeyFormattingUtils.State;
@@ -373,6 +375,11 @@ public class ViewKeyActivity extends BaseActivity implements
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
private void invokeNfcBeam() {
+ // Check if device supports NFC
+ if (!getPackageManager().hasSystemFeature(PackageManager.FEATURE_NFC)) {
+ Notify.createNotify(this, R.string.no_nfc_support, Notify.LENGTH_LONG, Notify.Style.ERROR).show();
+ return;
+ }
// Check for available NFC Adapter
mNfcAdapter = NfcAdapter.getDefaultAdapter(this);
if (mNfcAdapter == null || !mNfcAdapter.isEnabled()) {
@@ -429,7 +436,7 @@ public class ViewKeyActivity extends BaseActivity implements
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
Bundle data = message.getData();
CertifyResult result = data.getParcelable(CertifyResult.EXTRA_RESULT);
@@ -486,7 +493,7 @@ public class ViewKeyActivity extends BaseActivity implements
Handler returnHandler = new Handler() {
@Override
public void handleMessage(Message message) {
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
setResult(RESULT_CANCELED);
finish();
}
@@ -595,7 +602,7 @@ public class ViewKeyActivity extends BaseActivity implements
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle returnData = message.getData();
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyFragment.java
index bb3df2541..c3a8d60f8 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyFragment.java
@@ -44,6 +44,8 @@ import org.sufficientlysecure.keychain.ui.dialog.UserIdInfoDialogFragment;
import org.sufficientlysecure.keychain.util.ContactHelper;
import org.sufficientlysecure.keychain.util.Log;
+import java.util.List;
+
public class ViewKeyFragment extends LoaderFragment implements
LoaderManager.LoaderCallbacks<Cursor> {
@@ -53,7 +55,7 @@ public class ViewKeyFragment extends LoaderFragment implements
//private ListView mLinkedSystemContact;
boolean mIsSecret = false;
- private String mName;
+ boolean mSystemContactLoaded = false;
LinearLayout mSystemContactLayout;
ImageView mSystemContactPicture;
@@ -119,28 +121,48 @@ public class ViewKeyFragment extends LoaderFragment implements
/**
* Checks if a system contact exists for given masterKeyId, and if it does, sets name, picture
* and onClickListener for the linked system contact's layout
+ * In the case of a secret key, "me" contact details are loaded
*
- * @param name
* @param masterKeyId
*/
- private void loadLinkedSystemContact(String name, final long masterKeyId) {
+ private void loadLinkedSystemContact(final long masterKeyId) {
final Context context = mSystemContactName.getContext();
final ContentResolver resolver = context.getContentResolver();
- final long contactId = ContactHelper.findContactId(resolver, masterKeyId);
+ long contactId;
+ String contactName = null;
+
+ if (mIsSecret) {//all secret keys are linked to "me" profile in contacts
+ contactId = ContactHelper.getMainProfileContactId(resolver);
+ List<String> mainProfileNames = ContactHelper.getMainProfileContactName(context);
+ if (mainProfileNames != null && mainProfileNames.size() > 0) {
+ contactName = mainProfileNames.get(0);
+ }
- if (contactId != -1) {//contact exists for given master key
- mSystemContactName.setText(name);
+ } else {
+ contactId = ContactHelper.findContactId(resolver, masterKeyId);
+ contactName = ContactHelper.getContactName(resolver, contactId);
+ }
- Bitmap picture = ContactHelper.loadPhotoByMasterKeyId(resolver, masterKeyId, true);
+ if (contactName != null) {//contact name exists for given master key
+ mSystemContactName.setText(contactName);
+
+ Bitmap picture;
+ if (mIsSecret) {
+ picture = ContactHelper.loadMainProfilePhoto(resolver, false);
+ } else {
+ picture = ContactHelper.loadPhotoByMasterKeyId(resolver, masterKeyId, false);
+ }
if (picture != null) mSystemContactPicture.setImageBitmap(picture);
+ final long finalContactId = contactId;
mSystemContactLayout.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
- launchContactActivity(contactId, context);
+ launchContactActivity(finalContactId, context);
}
});
+ mSystemContactLoaded = true;
}
}
@@ -240,11 +262,11 @@ public class ViewKeyFragment extends LoaderFragment implements
if (data.moveToFirst()) {
mIsSecret = data.getInt(INDEX_HAS_ANY_SECRET) != 0;
- if (mName == null) {//to ensure we load the linked system contact only once
- String[] mainUserId = KeyRing.splitUserId(data.getString(INDEX_USER_ID));
- mName = mainUserId[0];
+
+ //TODO system to allow immediate refreshing of system contact on verification
+ if (!mSystemContactLoaded) {//ensure we load linked system contact only once
long masterKeyId = data.getLong(INDEX_MASTER_KEY_ID);
- loadLinkedSystemContact(mName, masterKeyId);
+ loadLinkedSystemContact(masterKeyId);
}
// load user ids after we know if it's a secret key
mUserIdsAdapter = new UserIdsAdapter(getActivity(), null, 0, !mIsSecret, null);
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyTrustFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyTrustFragment.java
index d22f01a48..e20796f8f 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyTrustFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/ViewKeyTrustFragment.java
@@ -368,7 +368,7 @@ public class ViewKeyTrustFragment extends LoaderFragment implements
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
Bundle returnData = message.getData();
String msg = returnData.getString(KeychainIntentServiceHandler.DATA_MESSAGE);
SpannableStringBuilder ssb = new SpannableStringBuilder();
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteFileDialogFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteFileDialogFragment.java
index c4b437593..bd4e5577b 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteFileDialogFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteFileDialogFragment.java
@@ -18,7 +18,6 @@
package org.sufficientlysecure.keychain.ui.dialog;
import android.app.Dialog;
-import android.content.ContentResolver;
import android.content.DialogInterface;
import android.net.Uri;
import android.os.Build;
@@ -34,18 +33,22 @@ import org.sufficientlysecure.keychain.util.FileHelper;
import org.sufficientlysecure.keychain.util.Log;
import java.io.File;
+import java.util.ArrayList;
+import java.util.HashMap;
public class DeleteFileDialogFragment extends DialogFragment {
- private static final String ARG_DELETE_URI = "delete_uri";
+ private static final String ARG_DELETE_URIS = "delete_uris";
+
+ private OnDeletedListener onDeletedListener;
/**
* Creates new instance of this delete file dialog fragment
*/
- public static DeleteFileDialogFragment newInstance(Uri deleteUri) {
+ public static DeleteFileDialogFragment newInstance(Uri... deleteUris) {
DeleteFileDialogFragment frag = new DeleteFileDialogFragment();
Bundle args = new Bundle();
- args.putParcelable(ARG_DELETE_URI, deleteUri);
+ args.putParcelableArray(ARG_DELETE_URIS, deleteUris);
frag.setArguments(args);
@@ -59,12 +62,21 @@ public class DeleteFileDialogFragment extends DialogFragment {
public Dialog onCreateDialog(Bundle savedInstanceState) {
final FragmentActivity activity = getActivity();
- final Uri deleteUri = getArguments().getParcelable(ARG_DELETE_URI);
- final String deleteFilename = FileHelper.getFilename(getActivity(), deleteUri);
+ final Uri[] deleteUris = (Uri[]) getArguments().getParcelableArray(ARG_DELETE_URIS);
+
+ final StringBuilder deleteFileNames = new StringBuilder();
+ //Retrieving file names after deletion gives unexpected results
+ final HashMap<Uri, String> deleteFileNameMap = new HashMap<>();
+ for (Uri deleteUri : deleteUris) {
+ String deleteFileName = FileHelper.getFilename(getActivity(), deleteUri);
+ deleteFileNames.append('\n').append(deleteFileName);
+ deleteFileNameMap.put(deleteUri, deleteFileName);
+ }
CustomAlertDialogBuilder alert = new CustomAlertDialogBuilder(activity);
- alert.setMessage(this.getString(R.string.file_delete_confirmation, deleteFilename));
+ alert.setTitle(getString(R.string.file_delete_confirmation_title));
+ alert.setMessage(getString(R.string.file_delete_confirmation, deleteFileNames.toString()));
alert.setPositiveButton(R.string.btn_delete, new DialogInterface.OnClickListener() {
@@ -72,43 +84,55 @@ public class DeleteFileDialogFragment extends DialogFragment {
public void onClick(DialogInterface dialog, int id) {
dismiss();
- // NOTE: Use Toasts, not Snackbars. When sharing to another application snackbars
- // would not show up!
+ ArrayList<String> failedFileNameList = new ArrayList<>();
+
+ for (Uri deleteUri : deleteUris) {
+ // Use DocumentsContract on Android >= 4.4
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
+ try {
+ if (DocumentsContract.deleteDocument(getActivity().getContentResolver(), deleteUri)) {
+ continue;
+ }
+ } catch (Exception e) {
+ Log.d(Constants.TAG, "Catched Exception, can happen when delete is not supported!", e);
+ }
+ }
- // Use DocumentsContract on Android >= 4.4
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
try {
- if (DocumentsContract.deleteDocument(getActivity().getContentResolver(), deleteUri)) {
- Toast.makeText(getActivity(), getActivity().getString(R.string.file_delete_successful,
- deleteFilename), Toast.LENGTH_LONG).show();
- return;
+ if (getActivity().getContentResolver().delete(deleteUri, null, null) > 0) {
+ continue;
}
- } catch (UnsupportedOperationException e) {
- Log.d(Constants.TAG, "Catched UnsupportedOperationException, can happen when delete is not supported!", e);
+ } catch (Exception e) {
+ Log.d(Constants.TAG, "Catched Exception, can happen when delete is not supported!", e);
}
- }
- try {
- if (getActivity().getContentResolver().delete(deleteUri, null, null) > 0) {
- Toast.makeText(getActivity(), getActivity().getString(R.string.file_delete_successful,
- deleteFilename), Toast.LENGTH_LONG).show();
- return;
+ // some Uri's a ContentResolver fails to delete is handled by the java.io.File's delete
+ // via the path of the Uri
+ if (new File(deleteUri.getPath()).delete()) {
+ continue;
}
- } catch (UnsupportedOperationException e) {
- Log.d(Constants.TAG, "Catched UnsupportedOperationException, can happen when delete is not supported!", e);
+
+ // Note: We can't delete every file...
+ failedFileNameList.add(deleteFileNameMap.get(deleteUri));
}
- // some Uri's a ContentResolver fails to delete is handled by the java.io.File's delete
- // via the path of the Uri
- if (new File(deleteUri.getPath()).delete()) {
- Toast.makeText(getActivity(), getActivity().getString(R.string.file_delete_successful,
- deleteFilename), Toast.LENGTH_LONG).show();
- return;
+ StringBuilder failedFileNames = new StringBuilder();
+ if (!failedFileNameList.isEmpty()) {
+ for (String failedFileName : failedFileNameList) {
+ failedFileNames.append('\n').append(failedFileName);
+ }
+ failedFileNames.append('\n').append(getActivity().getString(R.string.error_file_delete_failed));
}
- // Note: We can't delete every file...
- Toast.makeText(getActivity(), getActivity().getString(R.string.error_file_delete_failed,
- deleteFilename), Toast.LENGTH_LONG).show();
+ // NOTE: Use Toasts, not Snackbars. When sharing to another application snackbars
+ // would not show up!
+ Toast.makeText(getActivity(), getActivity().getString(R.string.file_delete_successful,
+ deleteUris.length - failedFileNameList.size(), deleteUris.length, failedFileNames.toString()),
+ Toast.LENGTH_LONG).show();
+
+ if (onDeletedListener != null) {
+ onDeletedListener.onDeleted();
+ }
}
});
alert.setNegativeButton(android.R.string.cancel, new DialogInterface.OnClickListener() {
@@ -120,4 +144,18 @@ public class DeleteFileDialogFragment extends DialogFragment {
return alert.show();
}
+
+ public void setOnDeletedListener(OnDeletedListener onDeletedListener) {
+ this.onDeletedListener = onDeletedListener;
+ }
+
+ /**
+ * Callback for performing tasks after the deletion of files
+ */
+ public interface OnDeletedListener {
+
+ public void onDeleted();
+
+ }
+
}
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteKeyDialogFragment.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteKeyDialogFragment.java
index 32789d53b..20f20c32e 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteKeyDialogFragment.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/dialog/DeleteKeyDialogFragment.java
@@ -142,7 +142,7 @@ public class DeleteKeyDialogFragment extends DialogFragment {
public void handleMessage(Message message) {
super.handleMessage(message);
// handle messages by standard KeychainIntentServiceHandler first
- if (message.arg1 == MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
try {
Message msg = Message.obtain();
msg.copyFrom(message);
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/CertifyKeySpinner.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/CertifyKeySpinner.java
index 6dd254aa1..fb6b84f58 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/CertifyKeySpinner.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/CertifyKeySpinner.java
@@ -68,7 +68,9 @@ public class CertifyKeySpinner extends KeySpinner {
KeychainContract.KeyRings.IS_REVOKED,
KeychainContract.KeyRings.IS_EXPIRED,
KeychainContract.KeyRings.HAS_CERTIFY,
- KeychainContract.KeyRings.HAS_ANY_SECRET
+ KeychainContract.KeyRings.HAS_ANY_SECRET,
+ KeychainContract.KeyRings.HAS_DUPLICATE_USER_ID,
+ KeychainContract.KeyRings.CREATION
};
String where = KeychainContract.KeyRings.HAS_ANY_SECRET + " = 1 AND "
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/KeySpinner.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/KeySpinner.java
index c8eceea50..ab5b02301 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/KeySpinner.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/KeySpinner.java
@@ -25,6 +25,7 @@ import android.support.v4.app.LoaderManager;
import android.support.v4.content.Loader;
import android.support.v4.widget.CursorAdapter;
import android.support.v7.internal.widget.TintSpinner;
+import android.text.format.DateFormat;
import android.util.AttributeSet;
import android.view.View;
import android.view.ViewGroup;
@@ -41,6 +42,10 @@ import org.sufficientlysecure.keychain.provider.KeychainContract;
import org.sufficientlysecure.keychain.ui.util.KeyFormattingUtils;
import org.sufficientlysecure.keychain.util.Log;
+import java.util.Calendar;
+import java.util.Date;
+import java.util.TimeZone;
+
/**
* Use TintSpinner from AppCompat lib instead of Spinner. Fixes white dropdown icon.
* Related: http://stackoverflow.com/a/27713090
@@ -139,11 +144,12 @@ public abstract class KeySpinner extends TintSpinner implements LoaderManager.Lo
protected class SelectKeyAdapter extends BaseAdapter implements SpinnerAdapter {
private CursorAdapter inner;
private int mIndexUserId;
- private int mIndexKeyId;
+ private int mIndexDuplicate;
private int mIndexMasterKeyId;
+ private int mIndexCreationDate;
public SelectKeyAdapter() {
- inner = new CursorAdapter(null, null, 0) {
+ inner = new CursorAdapter(getContext(), null, 0) {
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
return View.inflate(getContext(), R.layout.keyspinner_item, null);
@@ -154,12 +160,26 @@ public abstract class KeySpinner extends TintSpinner implements LoaderManager.Lo
TextView vKeyName = (TextView) view.findViewById(R.id.keyspinner_key_name);
ImageView vKeyStatus = (ImageView) view.findViewById(R.id.keyspinner_key_status);
TextView vKeyEmail = (TextView) view.findViewById(R.id.keyspinner_key_email);
- TextView vKeyId = (TextView) view.findViewById(R.id.keyspinner_key_id);
+ TextView vDuplicate = (TextView) view.findViewById(R.id.keyspinner_duplicate);
String[] userId = KeyRing.splitUserId(cursor.getString(mIndexUserId));
vKeyName.setText(userId[2] == null ? userId[0] : (userId[0] + " (" + userId[2] + ")"));
vKeyEmail.setText(userId[1]);
- vKeyId.setText(KeyFormattingUtils.beautifyKeyIdWithPrefix(getContext(), cursor.getLong(mIndexKeyId)));
+
+ boolean duplicate = cursor.getLong(mIndexDuplicate) > 0;
+ if (duplicate) {
+ Date creationDate = new Date(cursor.getLong(mIndexCreationDate) * 1000);
+ Calendar creationCal = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
+ creationCal.setTime(creationDate);
+ // convert from UTC to time zone of device
+ creationCal.setTimeZone(TimeZone.getDefault());
+
+ vDuplicate.setText(context.getString(R.string.label_creation) + ": "
+ + DateFormat.getDateFormat(context).format(creationCal.getTime()));
+ vDuplicate.setVisibility(View.VISIBLE);
+ } else {
+ vDuplicate.setVisibility(View.GONE);
+ }
boolean valid = setStatus(getContext(), cursor, vKeyStatus);
setItemEnabled(view, valid);
@@ -181,18 +201,18 @@ public abstract class KeySpinner extends TintSpinner implements LoaderManager.Lo
TextView vKeyName = (TextView) view.findViewById(R.id.keyspinner_key_name);
ImageView vKeyStatus = (ImageView) view.findViewById(R.id.keyspinner_key_status);
TextView vKeyEmail = (TextView) view.findViewById(R.id.keyspinner_key_email);
- TextView vKeyId = (TextView) view.findViewById(R.id.keyspinner_key_id);
+ TextView vKeyDuplicate = (TextView) view.findViewById(R.id.keyspinner_duplicate);
if (enabled) {
vKeyName.setTextColor(Color.BLACK);
vKeyEmail.setTextColor(Color.BLACK);
- vKeyId.setTextColor(Color.BLACK);
+ vKeyDuplicate.setTextColor(Color.BLACK);
vKeyStatus.setVisibility(View.GONE);
view.setClickable(false);
} else {
vKeyName.setTextColor(Color.GRAY);
vKeyEmail.setTextColor(Color.GRAY);
- vKeyId.setTextColor(Color.GRAY);
+ vKeyDuplicate.setTextColor(Color.GRAY);
vKeyStatus.setVisibility(View.VISIBLE);
// this is a HACK. the trick is, if the element itself is clickable, the
// click is not passed on to the view list
@@ -203,9 +223,10 @@ public abstract class KeySpinner extends TintSpinner implements LoaderManager.Lo
public Cursor swapCursor(Cursor newCursor) {
if (newCursor == null) return inner.swapCursor(null);
- mIndexKeyId = newCursor.getColumnIndex(KeychainContract.KeyRings.KEY_ID);
+ mIndexDuplicate = newCursor.getColumnIndex(KeychainContract.KeyRings.HAS_DUPLICATE_USER_ID);
mIndexUserId = newCursor.getColumnIndex(KeychainContract.KeyRings.USER_ID);
mIndexMasterKeyId = newCursor.getColumnIndex(KeychainContract.KeyRings.MASTER_KEY_ID);
+ mIndexCreationDate = newCursor.getColumnIndex(KeychainContract.KeyRings.CREATION);
if (newCursor.moveToFirst()) {
do {
if (newCursor.getLong(mIndexMasterKeyId) == mSelectedKeyId) {
@@ -257,19 +278,17 @@ public abstract class KeySpinner extends TintSpinner implements LoaderManager.Lo
TextView vKeyName = (TextView) view.findViewById(R.id.keyspinner_key_name);
ImageView vKeyStatus = (ImageView) view.findViewById(R.id.keyspinner_key_status);
TextView vKeyEmail = (TextView) view.findViewById(R.id.keyspinner_key_email);
- TextView vKeyId = (TextView) view.findViewById(R.id.keyspinner_key_id);
+ TextView vKeyDuplicate = (TextView) view.findViewById(R.id.keyspinner_duplicate);
vKeyName.setText(R.string.choice_none);
vKeyEmail.setVisibility(View.GONE);
- vKeyId.setVisibility(View.GONE);
+ vKeyDuplicate.setVisibility(View.GONE);
vKeyStatus.setVisibility(View.GONE);
setItemEnabled(view, true);
} else {
view = inner.getView(position - 1, convertView, parent);
TextView vKeyEmail = (TextView) view.findViewById(R.id.keyspinner_key_email);
- TextView vKeyId = (TextView) view.findViewById(R.id.keyspinner_key_id);
vKeyEmail.setVisibility(View.VISIBLE);
- vKeyId.setVisibility(View.VISIBLE);
}
return view;
}
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/SignKeySpinner.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/SignKeySpinner.java
index 10327a6a4..df7347fa4 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/SignKeySpinner.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/ui/widget/SignKeySpinner.java
@@ -59,7 +59,9 @@ public class SignKeySpinner extends KeySpinner {
KeychainContract.KeyRings.IS_REVOKED,
KeychainContract.KeyRings.IS_EXPIRED,
KeychainContract.KeyRings.HAS_SIGN,
- KeychainContract.KeyRings.HAS_ANY_SECRET
+ KeychainContract.KeyRings.HAS_ANY_SECRET,
+ KeychainContract.KeyRings.HAS_DUPLICATE_USER_ID,
+ KeychainContract.KeyRings.CREATION
};
String where = KeychainContract.KeyRings.HAS_ANY_SECRET + " = 1";
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ContactHelper.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ContactHelper.java
index 1413273e8..6efc0a5ea 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ContactHelper.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ContactHelper.java
@@ -190,7 +190,7 @@ public class ContactHelper {
* @param context
* @return
*/
- private static List<String> getMainProfileContactName(Context context) {
+ public static List<String> getMainProfileContactName(Context context) {
ContentResolver resolver = context.getContentResolver();
Cursor profileCursor = resolver.query(
ContactsContract.Profile.CONTENT_URI,
@@ -214,6 +214,55 @@ public class ContactHelper {
return new ArrayList<>(names);
}
+ /**
+ * returns the CONTACT_ID of the main ("me") contact
+ * http://developer.android.com/reference/android/provider/ContactsContract.Profile.html
+ *
+ * @param resolver
+ * @return
+ */
+ public static long getMainProfileContactId(ContentResolver resolver) {
+ Cursor profileCursor = resolver.query(ContactsContract.Profile.CONTENT_URI,
+ new String[]{ ContactsContract.Profile._ID}, null, null, null);
+
+ if(profileCursor != null && profileCursor.getCount() != 0 && profileCursor.moveToNext()) {
+ long contactId = profileCursor.getLong(0);
+ profileCursor.close();
+ return contactId;
+ }
+ else {
+ if(profileCursor != null) {
+ profileCursor.close();
+ }
+ return -1;
+ }
+ }
+
+ /**
+ * loads the profile picture of the main ("me") contact
+ * http://developer.android.com/reference/android/provider/ContactsContract.Profile.html
+ *
+ * @param contentResolver
+ * @param highRes true for large image if present, false for thumbnail
+ * @return bitmap of loaded photo
+ */
+ public static Bitmap loadMainProfilePhoto(ContentResolver contentResolver, boolean highRes) {
+ try {
+ long mainProfileContactId = getMainProfileContactId(contentResolver);
+
+ Uri contactUri = Uri.withAppendedPath(ContactsContract.Contacts.CONTENT_URI,
+ Long.toString(mainProfileContactId));
+ InputStream photoInputStream =
+ ContactsContract.Contacts.openContactPhotoInputStream(contentResolver, contactUri, highRes);
+ if (photoInputStream == null) {
+ return null;
+ }
+ return BitmapFactory.decodeStream(photoInputStream);
+ } catch (Throwable ignored) {
+ return null;
+ }
+ }
+
public static List<String> getContactMails(Context context) {
ContentResolver resolver = context.getContentResolver();
Cursor mailCursor = resolver.query(ContactsContract.CommonDataKinds.Email.CONTENT_URI,
@@ -269,7 +318,7 @@ public class ContactHelper {
/**
* returns the CONTACT_ID of the raw contact to which a masterKeyId is associated, if the
- * raw contact has not been marked for deletion
+ * raw contact has not been marked for deletion.
*
* @param resolver
* @param masterKeyId
@@ -296,6 +345,34 @@ public class ContactHelper {
return contactId;
}
+ /**
+ * Returns the display name of the system contact associated with contactId, null if the
+ * contact does not exist
+ *
+ * @param resolver
+ * @param contactId
+ * @return primary display name of system contact associated with contactId, null if it does
+ * not exist
+ */
+ public static String getContactName(ContentResolver resolver, long contactId) {
+ String contactName = null;
+ Cursor raw = resolver.query(ContactsContract.Contacts.CONTENT_URI,
+ new String[]{
+ ContactsContract.Contacts.DISPLAY_NAME_PRIMARY
+ },
+ ContactsContract.Contacts._ID + "=?",
+ new String[]{//"0" for "not deleted"
+ Long.toString(contactId)
+ }, null);
+ if (raw != null) {
+ if (raw.moveToNext()) {
+ contactName = raw.getString(0);
+ }
+ raw.close();
+ }
+ return contactName;
+ }
+
public static Bitmap getCachedPhotoByMasterKeyId(ContentResolver contentResolver, long masterKeyId) {
if (masterKeyId == -1) {
return null;
@@ -333,46 +410,47 @@ public class ContactHelper {
KeychainContract.KeyRings.MASTER_KEY_ID,
KeychainContract.KeyRings.USER_ID,
KeychainContract.KeyRings.IS_EXPIRED,
- KeychainContract.KeyRings.IS_REVOKED};
+ KeychainContract.KeyRings.IS_REVOKED,
+ KeychainContract.KeyRings.VERIFIED,
+ KeychainContract.KeyRings.HAS_SECRET,
+ KeychainContract.KeyRings.HAS_ANY_SECRET};
public static final int INDEX_MASTER_KEY_ID = 0;
public static final int INDEX_USER_ID = 1;
public static final int INDEX_IS_EXPIRED = 2;
public static final int INDEX_IS_REVOKED = 3;
+ public static final int INDEX_VERIFIED = 4;
+ public static final int INDEX_HAS_SECRET = 5;
+ public static final int INDEX_HAS_ANY_SECRET = 6;
/**
* Write/Update the current OpenKeychain keys to the contact db
*/
public static void writeKeysToContacts(Context context) {
ContentResolver resolver = context.getContentResolver();
- Set<Long> deletedKeys = getRawContactMasterKeyIds(resolver);
if (Constants.DEBUG_SYNC_REMOVE_CONTACTS) {
debugDeleteRawContacts(resolver);
}
-// ContentProviderClient client = resolver.acquireContentProviderClient(ContactsContract.AUTHORITY_URI);
-// ContentValues values = new ContentValues();
-// Account account = new Account(Constants.ACCOUNT_NAME, Constants.ACCOUNT_TYPE);
-// values.put(ContactsContract.Settings.ACCOUNT_NAME, account.name);
-// values.put(ContactsContract.Settings.ACCOUNT_TYPE, account.type);
-// values.put(ContactsContract.Settings.UNGROUPED_VISIBLE, true);
-// try {
-// client.insert(ContactsContract.Settings.CONTENT_URI.buildUpon().appendQueryParameter(ContactsContract.CALLER_IS_SYNCADAPTER, "true").build(), values);
-// } catch (RemoteException e) {
-// e.printStackTrace();
-// }
-
- // Load all Keys from OK
- Cursor cursor = resolver.query(KeychainContract.KeyRings.buildUnifiedKeyRingsUri(), KEYS_TO_CONTACT_PROJECTION,
- null, null, null);
+ writeKeysToMainProfileContact(context, resolver);
+
+ Set<Long> deletedKeys = getRawContactMasterKeyIds(resolver);
+
+ // Load all public Keys from OK
+ // TODO: figure out why using selectionArgs does not work in this case
+ Cursor cursor = resolver.query(KeychainContract.KeyRings.buildUnifiedKeyRingsUri(),
+ KEYS_TO_CONTACT_PROJECTION,
+ KeychainContract.KeyRings.HAS_ANY_SECRET + "=0",
+ null, null);
+
if (cursor != null) {
while (cursor.moveToNext()) {
long masterKeyId = cursor.getLong(INDEX_MASTER_KEY_ID);
String[] userIdSplit = KeyRing.splitUserId(cursor.getString(INDEX_USER_ID));
- String keyIdShort = KeyFormattingUtils.convertKeyIdToHexShort(cursor.getLong(INDEX_MASTER_KEY_ID));
boolean isExpired = cursor.getInt(INDEX_IS_EXPIRED) != 0;
boolean isRevoked = cursor.getInt(INDEX_IS_REVOKED) > 0;
+ boolean isVerified = cursor.getInt(INDEX_VERIFIED) > 0;
Log.d(Constants.TAG, "masterKeyId: " + masterKeyId);
@@ -384,9 +462,11 @@ public class ContactHelper {
ArrayList<ContentProviderOperation> ops = new ArrayList<>();
- // Do not store expired or revoked keys in contact db - and remove them if they already exist
- if (isExpired || isRevoked) {
- Log.d(Constants.TAG, "Expired or revoked: Deleting rawContactId " + rawContactId);
+ // Do not store expired or revoked or unverified keys in contact db - and
+ // remove them if they already exist. Secret keys do not reach this point
+ if (isExpired || isRevoked || !isVerified) {
+ Log.d(Constants.TAG, "Expired or revoked or unverified: Deleting rawContactId "
+ + rawContactId);
if (rawContactId != -1) {
deleteRawContactById(resolver, rawContactId);
}
@@ -397,7 +477,7 @@ public class ContactHelper {
Log.d(Constants.TAG, "Insert new raw contact with masterKeyId " + masterKeyId);
insertContact(ops, context, masterKeyId);
- writeContactKey(ops, context, rawContactId, masterKeyId, keyIdShort);
+ writeContactKey(ops, context, rawContactId, masterKeyId, userIdSplit[0]);
}
// We always update the display name (which is derived from primary user id)
@@ -422,43 +502,165 @@ public class ContactHelper {
}
/**
- * Delete all raw contacts associated to OpenKeychain.
+ * Links all keys with secrets to the main ("me") contact
+ * http://developer.android.com/reference/android/provider/ContactsContract.Profile.html
+ *
+ * @param context
+ */
+ public static void writeKeysToMainProfileContact(Context context, ContentResolver resolver) {
+ Set<Long> keysToDelete = getMainProfileMasterKeyIds(resolver);
+
+ // get all keys which have associated secret keys
+ // TODO: figure out why using selectionArgs does not work in this case
+ Cursor cursor = resolver.query(KeychainContract.KeyRings.buildUnifiedKeyRingsUri(),
+ KEYS_TO_CONTACT_PROJECTION,
+ KeychainContract.KeyRings.HAS_ANY_SECRET + "!=0",
+ null, null);
+ if (cursor != null) {
+ while (cursor.moveToNext()) {
+ long masterKeyId = cursor.getLong(INDEX_MASTER_KEY_ID);
+ boolean isExpired = cursor.getInt(INDEX_IS_EXPIRED) != 0;
+ boolean isRevoked = cursor.getInt(INDEX_IS_REVOKED) > 0;
+ String[] userIdSplit = KeyRing.splitUserId(cursor.getString(INDEX_USER_ID));
+
+ if (!isExpired && !isRevoked && userIdSplit[0] != null) {
+ // if expired or revoked will not be removed from keysToDelete or inserted
+ // into main profile ("me" contact)
+ boolean existsInMainProfile = keysToDelete.remove(masterKeyId);
+ if (!existsInMainProfile) {
+ long rawContactId = -1;//new raw contact
+
+ Log.d(Constants.TAG, "masterKeyId with secret " + masterKeyId);
+
+ ArrayList<ContentProviderOperation> ops = new ArrayList<>();
+ insertMainProfileRawContact(ops, masterKeyId);
+ writeContactKey(ops, context, rawContactId, masterKeyId, userIdSplit[0]);
+
+ try {
+ resolver.applyBatch(ContactsContract.AUTHORITY, ops);
+ } catch (Exception e) {
+ Log.w(Constants.TAG, e);
+ }
+ }
+ }
+ }
+ }
+
+ for (long masterKeyId : keysToDelete) {
+ deleteMainProfileRawContactByMasterKeyId(resolver, masterKeyId);
+ Log.d(Constants.TAG, "Delete main profile raw contact with masterKeyId " + masterKeyId);
+ }
+ }
+
+ /**
+ * Inserts a raw contact into the table defined by ContactsContract.Profile
+ * http://developer.android.com/reference/android/provider/ContactsContract.Profile.html
+ *
+ * @param ops
+ * @param masterKeyId
+ */
+ private static void insertMainProfileRawContact(ArrayList<ContentProviderOperation> ops,
+ long masterKeyId) {
+ ops.add(ContentProviderOperation.newInsert(ContactsContract.Profile.CONTENT_RAW_CONTACTS_URI)
+ .withValue(ContactsContract.RawContacts.ACCOUNT_NAME, Constants.ACCOUNT_NAME)
+ .withValue(ContactsContract.RawContacts.ACCOUNT_TYPE, Constants.ACCOUNT_TYPE)
+ .withValue(ContactsContract.RawContacts.SOURCE_ID, Long.toString(masterKeyId))
+ .build());
+ }
+
+ /**
+ * deletes a raw contact from the main profile table ("me" contact)
+ * http://developer.android.com/reference/android/provider/ContactsContract.Profile.html
+ *
+ * @param resolver
+ * @param masterKeyId
+ * @return
+ */
+ private static int deleteMainProfileRawContactByMasterKeyId(ContentResolver resolver,
+ long masterKeyId) {
+ // CALLER_IS_SYNCADAPTER allows us to actually wipe the RawContact from the device, otherwise
+ // would be just flagged for deletion
+ Uri deleteUri = ContactsContract.Profile.CONTENT_RAW_CONTACTS_URI.buildUpon().
+ appendQueryParameter(ContactsContract.CALLER_IS_SYNCADAPTER, "true").build();
+
+ return resolver.delete(deleteUri,
+ ContactsContract.RawContacts.ACCOUNT_TYPE + "=? AND " +
+ ContactsContract.RawContacts.SOURCE_ID + "=?",
+ new String[]{
+ Constants.ACCOUNT_TYPE, Long.toString(masterKeyId)
+ });
+ }
+
+ /**
+ * Delete all raw contacts associated to OpenKeychain, including those from "me" contact
+ * defined by ContactsContract.Profile
+ *
+ * @return number of rows deleted
*/
private static int debugDeleteRawContacts(ContentResolver resolver) {
- //allows us to actually wipe the RawContact from the device, otherwise would be just flagged
- //for deletion
+ // CALLER_IS_SYNCADAPTER allows us to actually wipe the RawContact from the device, otherwise
+ // would be just flagged for deletion
Uri deleteUri = ContactsContract.RawContacts.CONTENT_URI.buildUpon().
appendQueryParameter(ContactsContract.CALLER_IS_SYNCADAPTER, "true").build();
Log.d(Constants.TAG, "Deleting all raw contacts associated to OK...");
- return resolver.delete(deleteUri,
+ int delete = resolver.delete(deleteUri,
+ ContactsContract.RawContacts.ACCOUNT_TYPE + "=?",
+ new String[]{
+ Constants.ACCOUNT_TYPE
+ });
+
+ Uri mainProfileDeleteUri = ContactsContract.Profile.CONTENT_RAW_CONTACTS_URI.buildUpon()
+ .appendQueryParameter(ContactsContract.CALLER_IS_SYNCADAPTER, "true").build();
+
+ delete += resolver.delete(mainProfileDeleteUri,
ContactsContract.RawContacts.ACCOUNT_TYPE + "=?",
new String[]{
Constants.ACCOUNT_TYPE
});
+
+ return delete;
}
+ /**
+ * Deletes raw contacts from ContactsContract.RawContacts based on rawContactId. Does not
+ * delete contacts from the "me" contact defined in ContactsContract.Profile
+ *
+ * @param resolver
+ * @param rawContactId
+ * @return number of rows deleted
+ */
private static int deleteRawContactById(ContentResolver resolver, long rawContactId) {
- //allows us to actually wipe the RawContact from the device, otherwise would be just flagged
- //for deletion
+ // CALLER_IS_SYNCADAPTER allows us to actually wipe the RawContact from the device, otherwise
+ // would be just flagged for deletion
Uri deleteUri = ContactsContract.RawContacts.CONTENT_URI.buildUpon().
appendQueryParameter(ContactsContract.CALLER_IS_SYNCADAPTER, "true").build();
return resolver.delete(deleteUri,
- ContactsContract.RawContacts.ACCOUNT_TYPE + "=? AND " + ContactsContract.RawContacts._ID + "=?",
+ ContactsContract.RawContacts.ACCOUNT_TYPE + "=? AND " +
+ ContactsContract.RawContacts._ID + "=?",
new String[]{
Constants.ACCOUNT_TYPE, Long.toString(rawContactId)
});
}
+ /**
+ * Deletes raw contacts from ContactsContract.RawContacts based on masterKeyId. Does not
+ * delete contacts from the "me" contact defined in ContactsContract.Profile
+ *
+ * @param resolver
+ * @param masterKeyId
+ * @return number of rows deleted
+ */
private static int deleteRawContactByMasterKeyId(ContentResolver resolver, long masterKeyId) {
- //allows us to actually wipe the RawContact from the device, otherwise would be just flagged
- //for deletion
+ // CALLER_IS_SYNCADAPTER allows us to actually wipe the RawContact from the device, otherwise
+ // would be just flagged for deletion
Uri deleteUri = ContactsContract.RawContacts.CONTENT_URI.buildUpon().
appendQueryParameter(ContactsContract.CALLER_IS_SYNCADAPTER, "true").build();
return resolver.delete(deleteUri,
- ContactsContract.RawContacts.ACCOUNT_TYPE + "=? AND " + ContactsContract.RawContacts.SOURCE_ID + "=?",
+ ContactsContract.RawContacts.ACCOUNT_TYPE + "=? AND " +
+ ContactsContract.RawContacts.SOURCE_ID + "=?",
new String[]{
Constants.ACCOUNT_TYPE, Long.toString(masterKeyId)
});
@@ -487,6 +689,28 @@ public class ContactHelper {
}
/**
+ * @return a set of all key master key ids currently present in the contact db
+ */
+ private static Set<Long> getMainProfileMasterKeyIds(ContentResolver resolver) {
+ HashSet<Long> result = new HashSet<>();
+ Cursor masterKeyIds = resolver.query(ContactsContract.Profile.CONTENT_RAW_CONTACTS_URI,
+ new String[]{
+ ContactsContract.RawContacts.SOURCE_ID
+ },
+ ContactsContract.RawContacts.ACCOUNT_TYPE + "=?",
+ new String[]{
+ Constants.ACCOUNT_TYPE
+ }, null);
+ if (masterKeyIds != null) {
+ while (masterKeyIds.moveToNext()) {
+ result.add(masterKeyIds.getLong(0));
+ }
+ masterKeyIds.close();
+ }
+ return result;
+ }
+
+ /**
* This will search the contact db for a raw contact with a given master key id
*
* @return raw contact id or -1 if not found
@@ -528,10 +752,10 @@ public class ContactHelper {
* This creates the link to OK in contact details
*/
private static void writeContactKey(ArrayList<ContentProviderOperation> ops, Context context, long rawContactId,
- long masterKeyId, String keyIdShort) {
+ long masterKeyId, String keyName) {
ops.add(referenceRawContact(ContentProviderOperation.newInsert(ContactsContract.Data.CONTENT_URI), rawContactId)
.withValue(ContactsContract.Data.MIMETYPE, Constants.CUSTOM_CONTACT_DATA_MIME_TYPE)
- .withValue(ContactsContract.Data.DATA1, context.getString(R.string.contact_show_key, keyIdShort))
+ .withValue(ContactsContract.Data.DATA1, context.getString(R.string.contact_show_key, keyName))
.withValue(ContactsContract.Data.DATA2, masterKeyId)
.build());
}
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ExportHelper.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ExportHelper.java
index 1d78ed80e..cda5892fe 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ExportHelper.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/util/ExportHelper.java
@@ -124,7 +124,7 @@ public class ExportHelper {
// handle messages by standard KeychainIntentServiceHandler first
super.handleMessage(message);
- if (message.arg1 == KeychainIntentServiceHandler.MESSAGE_OKAY) {
+ if (message.arg1 == MessageStatus.OKAY.ordinal()) {
// get returned data bundle
Bundle data = message.getData();
diff --git a/OpenKeychain/src/main/res/layout/keyspinner_item.xml b/OpenKeychain/src/main/res/layout/keyspinner_item.xml
index 45147e7b1..eea81eba5 100644
--- a/OpenKeychain/src/main/res/layout/keyspinner_item.xml
+++ b/OpenKeychain/src/main/res/layout/keyspinner_item.xml
@@ -36,8 +36,8 @@
android:textAppearance="?android:attr/textAppearanceSmall" />
<TextView
- android:id="@+id/keyspinner_key_id"
- android:text="12345"
+ android:id="@+id/keyspinner_duplicate"
+ android:text="creation: bla"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:singleLine="true"
diff --git a/OpenKeychain/src/main/res/values-cs/strings.xml b/OpenKeychain/src/main/res/values-cs/strings.xml
index 380dadb54..9c16fa413 100644
--- a/OpenKeychain/src/main/res/values-cs/strings.xml
+++ b/OpenKeychain/src/main/res/values-cs/strings.xml
@@ -173,8 +173,7 @@
<string name="pin_for">Zadat PIN pro \'%s\'</string>
<string name="yubikey_pin_for">Zadejte PIN pro přístup k YubiKey pro \'%s\'</string>
<string name="nfc_text">Přidržte YubiKey u zadní strany vašeho přístroje.</string>
- <string name="file_delete_confirmation">Chcete opravdu smazat\n%s?</string>
- <string name="no_file_selected">Nejprve vyberte soubor.</string>
+ <string name="no_file_selected">Nejprve vyberte soubor.</string>
<string name="encrypt_sign_successful">Úspěšně podepsáno a/nebo zašifrováno.</string>
<string name="encrypt_sign_clipboard_successful">Úspěšně podepsání a/nebo zašifrováno do schránky.</string>
<string name="select_encryption_key">Vyberte alespoň jeden šifrovací klíč.</string>
@@ -507,7 +506,8 @@
<string name="error_no_encrypt_subkey">Není dostupný šifrovací podklíč!</string>
<string name="contact_show_key">Zobrazit klíč (%s)</string>
<string name="swipe_to_update">Potáhnout dolů pro aktualizaci z keyserveru</string>
- <!--Passphrase wizard-->
+ <string name="file_delete_successful"></string>
+ <!--Passphrase wizard-->
<!--TODO: rename all the things!-->
<!--<string name="enter_passphrase_twice">Enter passphrase twice</string>-->
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
diff --git a/OpenKeychain/src/main/res/values-de/strings.xml b/OpenKeychain/src/main/res/values-de/strings.xml
index 98066b1e8..fbae159a3 100644
--- a/OpenKeychain/src/main/res/values-de/strings.xml
+++ b/OpenKeychain/src/main/res/values-de/strings.xml
@@ -190,8 +190,7 @@
<string name="pin_for">PIN für \'%s\' eingeben</string>
<string name="yubikey_pin_for">PIN für Zugriff auf Yubikey für \'%s\' eingeben</string>
<string name="nfc_text">Halten Sie den YubiKey gegen die Rückseite Ihres Geräts.</string>
- <string name="file_delete_confirmation">%s wirklich löschen?</string>
- <string name="no_file_selected">Zuerst eine Datei auswählen.</string>
+ <string name="no_file_selected">Zuerst eine Datei auswählen.</string>
<string name="encrypt_sign_successful">Erfolgreich signiert und/oder verschlüsselt.</string>
<string name="encrypt_sign_clipboard_successful">Erfolgreich in die Zwischenablage signiert und/oder verschlüsselt.</string>
<string name="select_encryption_key">Mindestens einen Schlüssel zum Verschlüsseln auswählen.</string>
@@ -1098,4 +1097,5 @@
<string name="nfc_write_succesful">Erfolgreich auf den NFC-Tag geschrieben</string>
<string name="unlocked">Entsperrt</string>
<string name="nfc_settings">Einstellungen</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-es/strings.xml b/OpenKeychain/src/main/res/values-es/strings.xml
index 92b958ad8..d7557074a 100644
--- a/OpenKeychain/src/main/res/values-es/strings.xml
+++ b/OpenKeychain/src/main/res/values-es/strings.xml
@@ -194,8 +194,7 @@
<string name="pin_for">Introduzca el PIN para \'%s\'</string>
<string name="yubikey_pin_for">Introduzca el PIN para acceder a la YubiKey para \'%s\'</string>
<string name="nfc_text">Sostenga la YubiKey contra el reverso de su dispositivo.</string>
- <string name="file_delete_confirmation">¿Está seguro de que quiere eliminar\n%s?</string>
- <string name="no_file_selected">Selecciona un archivo antes.</string>
+ <string name="no_file_selected">Selecciona un archivo antes.</string>
<string name="encrypt_sign_successful">Firmado y/o cifrado con éxito.</string>
<string name="encrypt_sign_clipboard_successful">Firmado y/o cifrado del portapapeles con éxito.</string>
<string name="select_encryption_key">Selecciona al menos una clave de cifrado.</string>
@@ -1145,4 +1144,5 @@
<string name="nfc_write_succesful">Se escribió con éxito en la etiqueta NFC</string>
<string name="unlocked">Desbloqueado</string>
<string name="nfc_settings">Configuración</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-et/strings.xml b/OpenKeychain/src/main/res/values-et/strings.xml
index 15b0c6c1e..f67ffb328 100644
--- a/OpenKeychain/src/main/res/values-et/strings.xml
+++ b/OpenKeychain/src/main/res/values-et/strings.xml
@@ -61,9 +61,11 @@
<string name="wrong_passphrase">Vale salasõne</string>
<string name="passphrases_do_not_match">Salasõned ei ühti.</string>
<string name="passphrase_for_symmetric_encryption">Sümmeetriline krüpteering</string>
- <!--errors
- no punctuation, all lowercase,
- they will be put after "error_message", e.g. "Error: file not found"-->
+ <string name="file_delete_successful"></string>
+ <string name="file_delete_confirmation"></string>
+ <!--errors
+ no punctuation, all lowercase,
+ they will be put after "error_message", e.g. "Error: file not found"-->
<!--errors without preceeding Error:-->
<!--results shown after decryption/verification-->
<!--Add keys-->
diff --git a/OpenKeychain/src/main/res/values-eu/strings.xml b/OpenKeychain/src/main/res/values-eu/strings.xml
index a09e3fdc5..32fdfc4cb 100644
--- a/OpenKeychain/src/main/res/values-eu/strings.xml
+++ b/OpenKeychain/src/main/res/values-eu/strings.xml
@@ -379,4 +379,6 @@
<string name="nfc_title">NFC</string>
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
<string name="nfc_settings">Ezarpenak</string>
+ <string name="file_delete_successful"></string>
+ <string name="file_delete_confirmation"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-fi/strings.xml b/OpenKeychain/src/main/res/values-fi/strings.xml
index 4313caf15..4b75d203d 100644
--- a/OpenKeychain/src/main/res/values-fi/strings.xml
+++ b/OpenKeychain/src/main/res/values-fi/strings.xml
@@ -169,9 +169,11 @@
<string name="passphrase_for_symmetric_encryption">Symmetrinen salaus.</string>
<string name="passphrase_for">Syötä salasana \'%s\':lle</string>
<string name="pin_for">Syötä PIN \'%s\':lle</string>
- <!--errors
- no punctuation, all lowercase,
- they will be put after "error_message", e.g. "Error: file not found"-->
+ <string name="file_delete_successful"></string>
+ <string name="file_delete_confirmation"></string>
+ <!--errors
+ no punctuation, all lowercase,
+ they will be put after "error_message", e.g. "Error: file not found"-->
<!--errors without preceeding Error:-->
<!--results shown after decryption/verification-->
<!--Add keys-->
diff --git a/OpenKeychain/src/main/res/values-fr/strings.xml b/OpenKeychain/src/main/res/values-fr/strings.xml
index f9ef4d41d..ba6f2e2af 100644
--- a/OpenKeychain/src/main/res/values-fr/strings.xml
+++ b/OpenKeychain/src/main/res/values-fr/strings.xml
@@ -194,8 +194,7 @@
<string name="pin_for">Saisir le NIP pour « %s »</string>
<string name="yubikey_pin_for">Saisir le NIP pour accéder à la Yubikey pour « %s »</string>
<string name="nfc_text">Tenez la YubiKey contre le dos de votre appareil.</string>
- <string name="file_delete_confirmation">Êtes-vous certain de vouloir supprimer\n%s?</string>
- <string name="no_file_selected">Choisir d\'abord un fichier.</string>
+ <string name="no_file_selected">Choisir d\'abord un fichier.</string>
<string name="encrypt_sign_successful">Signé et/ou chiffré avec succès.</string>
<string name="encrypt_sign_clipboard_successful">Signé et/ou chiffré vers le presse-papiers avec succès.</string>
<string name="select_encryption_key">Choisir au moins une clef de chiffrement.</string>
@@ -1136,4 +1135,5 @@
<string name="nfc_write_succesful">Écrit avec succès sur la balise NFC</string>
<string name="unlocked">Déverrouillé</string>
<string name="nfc_settings">Paramètres</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-it/strings.xml b/OpenKeychain/src/main/res/values-it/strings.xml
index 24c8a5657..5de5a1579 100644
--- a/OpenKeychain/src/main/res/values-it/strings.xml
+++ b/OpenKeychain/src/main/res/values-it/strings.xml
@@ -164,8 +164,7 @@
<string name="passphrase_must_not_be_empty">Si prega di inserire una frase di accesso.</string>
<string name="passphrase_for_symmetric_encryption">Codifica Simmetrica.</string>
<string name="passphrase_for">Inserisci la frase di accesso per \'%s\'</string>
- <string name="file_delete_confirmation">Sei sicuro di voler eliminare\n%s?</string>
- <string name="no_file_selected">Seleziona un file prima.</string>
+ <string name="no_file_selected">Seleziona un file prima.</string>
<string name="encrypt_sign_successful">Firmato e/o codificato con successo.</string>
<string name="encrypt_sign_clipboard_successful">Firmato e/o codificato con successo negli appunti.</string>
<string name="select_encryption_key">Seleziona almeno una chiave di codifica.</string>
@@ -715,7 +714,8 @@ Permetti accesso?\n\nATTENZIONE: Se non sai perche\' questo schermata e\' appars
<string name="error_no_file_selected">Seleziona almeno un file da codificare!</string>
<string name="error_multi_not_supported">Il salvataggio di più file non è supportato. Questa è una limitazione corrente di Android.</string>
<string name="key_colon">Chiave:</string>
- <!--Passphrase wizard-->
+ <string name="file_delete_successful"></string>
+ <!--Passphrase wizard-->
<!--TODO: rename all the things!-->
<!--<string name="enter_passphrase_twice">Enter passphrase twice</string>-->
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
diff --git a/OpenKeychain/src/main/res/values-ja/strings.xml b/OpenKeychain/src/main/res/values-ja/strings.xml
index 8a4778989..183938811 100644
--- a/OpenKeychain/src/main/res/values-ja/strings.xml
+++ b/OpenKeychain/src/main/res/values-ja/strings.xml
@@ -192,9 +192,7 @@
<string name="pin_for">\'%s\' にPINを入力してください</string>
<string name="yubikey_pin_for">\'%s\' の Yubikey にアクセスするためのPINを入力してください</string>
<string name="nfc_text">あなたのデバイスの背面にYubiKeyを固定してください。</string>
- <string name="file_delete_confirmation">%s
-を削除してもかまいませんか?</string>
- <string name="no_file_selected">最初にファイルを選択してください。</string>
+ <string name="no_file_selected">最初にファイルを選択してください。</string>
<string name="encrypt_sign_successful">署名/暗号化に成功しました。</string>
<string name="encrypt_sign_clipboard_successful">クリップボードの中身の署名/暗号化に成功しました。</string>
<string name="select_encryption_key">少なくとも1つの暗号化鍵を選択して下さい。</string>
@@ -1092,4 +1090,5 @@
<string name="nfc_write_succesful">NFCタグに書けました!</string>
<string name="unlocked">アンロック</string>
<string name="nfc_settings">設定</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-nl/strings.xml b/OpenKeychain/src/main/res/values-nl/strings.xml
index 4c1a6a8d1..0d3cb0094 100644
--- a/OpenKeychain/src/main/res/values-nl/strings.xml
+++ b/OpenKeychain/src/main/res/values-nl/strings.xml
@@ -204,9 +204,7 @@
<string name="pin_for">Voer PIN in voor \'%s\'</string>
<string name="yubikey_pin_for">Voer PIN in om toegang te verkrijgen tot YubiKey voor \'%s\'</string>
<string name="nfc_text">Hou YubiKey tegen de achterkant van je toestel</string>
- <string name="file_delete_confirmation">Ben je zeker dat je %s wil verwijderen?</string>
- <string name="file_delete_successful">\'%s\' is verwijderd.</string>
- <string name="no_file_selected">Selecteer eerst een bestand.</string>
+ <string name="no_file_selected">Selecteer eerst een bestand.</string>
<string name="encrypt_sign_successful">Succesvol gesigneerd en/of gecodeerd.</string>
<string name="encrypt_sign_clipboard_successful">Succesvol gesigneerd en/of gecodeerd naar klembord.</string>
<string name="select_encryption_key">Selecteer ten minste één versleutelingssleutel.</string>
@@ -239,8 +237,7 @@
<!--errors
no punctuation, all lowercase,
they will be put after "error_message", e.g. "Error: file not found"-->
- <string name="error_file_delete_failed">Verwijderen van \'%s\' mislukt. Gelieve dit handmatig te doen!</string>
- <string name="error_file_not_found">bestand niet gevonden</string>
+ <string name="error_file_not_found">bestand niet gevonden</string>
<string name="error_no_secret_key_found">geen geschikte privésleutel gevonden</string>
<string name="error_external_storage_not_ready">externe opslag niet gereed</string>
<string name="error_key_size_minimum512bit">sleutelgrootte moet minstens 512-bits zijn</string>
@@ -1159,4 +1156,5 @@
<string name="nfc_write_succesful">Succesvol geschreven op NFC-tag</string>
<string name="unlocked">Ontgrendeld</string>
<string name="nfc_settings">Instellingen</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-pl/strings.xml b/OpenKeychain/src/main/res/values-pl/strings.xml
index 8c0fc23d2..1ee5a86e7 100644
--- a/OpenKeychain/src/main/res/values-pl/strings.xml
+++ b/OpenKeychain/src/main/res/values-pl/strings.xml
@@ -179,8 +179,7 @@
<string name="passphrase_for">Podaj hasło dla \'%s\'</string>
<string name="pin_for">Wpisz PIN dla \'%s\'</string>
<string name="nfc_text">Trzymaj YubiKey z tyłu Twojego urządzenia.</string>
- <string name="file_delete_confirmation">Czy jesteś pewny, że chcesz usunąć\n%s?</string>
- <string name="no_file_selected">Najpierw wskaż plik.</string>
+ <string name="no_file_selected">Najpierw wskaż plik.</string>
<string name="encrypt_sign_successful">Pomyślnie podpisano i/lub zaszyfrowano.</string>
<string name="encrypt_sign_clipboard_successful">Pomyslnie podpisano i/lub zaszyfrowano do schowka.</string>
<string name="select_encryption_key">Wybierz co najmniej jeden klucz szyfrujący.</string>
@@ -657,7 +656,8 @@ OSTRZEŻENIE: Jeżeli nie wiesz, czemu wyświetlił się ten komunikat, nie zezw
<string name="error_no_file_selected">Wybierz przynajmniej jeden plik, aby szyfrować!</string>
<string name="key_colon">Klucz:</string>
<string name="btn_start_exchange">Rozpocznij wymianę</string>
- <!--Passphrase wizard-->
+ <string name="file_delete_successful"></string>
+ <!--Passphrase wizard-->
<!--TODO: rename all the things!-->
<!--<string name="enter_passphrase_twice">Enter passphrase twice</string>-->
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
diff --git a/OpenKeychain/src/main/res/values-ru/strings.xml b/OpenKeychain/src/main/res/values-ru/strings.xml
index f6658ded0..9559ecf51 100644
--- a/OpenKeychain/src/main/res/values-ru/strings.xml
+++ b/OpenKeychain/src/main/res/values-ru/strings.xml
@@ -192,8 +192,7 @@
<string name="yubikey_pin_for">Введите PIN для доступа к YubiKey для
\'%s\'</string>
<string name="nfc_text">Держите YubiKey возле задней части вашего устройства.</string>
- <string name="file_delete_confirmation">Вы уверены, что хотите удалить\n%s?</string>
- <string name="no_file_selected">Сначала выберите файл.</string>
+ <string name="no_file_selected">Сначала выберите файл.</string>
<string name="encrypt_sign_successful">Успешно подписано и/или зашифровано.</string>
<string name="encrypt_sign_clipboard_successful">Успешно подписано и/или зашифровано в буфер обмена.</string>
<string name="select_encryption_key">Укажите хотя бы один ключ.</string>
@@ -811,4 +810,5 @@
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
<string name="unlocked">Разблокирован</string>
<string name="nfc_settings">Настройки</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-sl/strings.xml b/OpenKeychain/src/main/res/values-sl/strings.xml
index 06f14a483..3eb8eeba8 100644
--- a/OpenKeychain/src/main/res/values-sl/strings.xml
+++ b/OpenKeychain/src/main/res/values-sl/strings.xml
@@ -168,8 +168,7 @@
<string name="passphrase_must_not_be_empty">Vnesite geslo.</string>
<string name="passphrase_for_symmetric_encryption">Simetrično šifriranje.</string>
<string name="passphrase_for">Vnesite geslo za \'%s\'</string>
- <string name="file_delete_confirmation">Ste prepričani, da želite izbrisati\n%s?</string>
- <string name="no_file_selected">Najprej izberite datoteko.</string>
+ <string name="no_file_selected">Najprej izberite datoteko.</string>
<string name="encrypt_sign_successful">Uspešno podpisano in/ali šifrirano.</string>
<string name="encrypt_sign_clipboard_successful">Uspešno podpisano in/ali šifrirano ter poslano v odložišče.</string>
<string name="select_encryption_key">Izberite vsaj en šifrirni ključ.</string>
@@ -479,7 +478,8 @@
<string name="error_no_encrypt_subkey">Ni nobenega podključa za šifriranje!</string>
<string name="contact_show_key">Prikaži ključ (%s)</string>
<string name="key_colon">Ključ:</string>
- <!--Passphrase wizard-->
+ <string name="file_delete_successful"></string>
+ <!--Passphrase wizard-->
<!--TODO: rename all the things!-->
<!--<string name="enter_passphrase_twice">Enter passphrase twice</string>-->
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
diff --git a/OpenKeychain/src/main/res/values-sr/strings.xml b/OpenKeychain/src/main/res/values-sr/strings.xml
index 73094c5a4..b5ba0b361 100644
--- a/OpenKeychain/src/main/res/values-sr/strings.xml
+++ b/OpenKeychain/src/main/res/values-sr/strings.xml
@@ -204,9 +204,7 @@
<string name="pin_for">Унесите ПИН за „%s“</string>
<string name="yubikey_pin_for">Унесите ПИН за приступ Јубикључу за „%s“</string>
<string name="nfc_text">Држите Јубикључ на полеђини вашег уређаја.</string>
- <string name="file_delete_confirmation">Желите ли заиста да обришете\n%s?</string>
- <string name="file_delete_successful">Брисање је успело.</string>
- <string name="no_file_selected">Најпре изаберите фајл.</string>
+ <string name="no_file_selected">Најпре изаберите фајл.</string>
<string name="encrypt_sign_successful">Потписивање и/или шифровање је успело.</string>
<string name="encrypt_sign_clipboard_successful">Потписивање и/или шифровање на клипборд је успело.</string>
<string name="enter_passphrase_twice">Унесите лозинку два пута.</string>
@@ -240,8 +238,7 @@
<!--errors
no punctuation, all lowercase,
they will be put after "error_message", e.g. "Error: file not found"-->
- <string name="error_file_delete_failed">брисање „%s“ није успело</string>
- <string name="error_file_not_found">фајл није нађен</string>
+ <string name="error_file_not_found">фајл није нађен</string>
<string name="error_no_secret_key_found">одговарајући тајни кључ није нађен</string>
<string name="error_external_storage_not_ready">спољашње складиште није спремно</string>
<string name="error_key_size_minimum512bit">величина кључа мора да буде најмање 512 бита</string>
@@ -1145,4 +1142,5 @@
<string name="nfc_write_succesful">Успешно уписах на НФЦ ознаку</string>
<string name="unlocked">Откључан</string>
<string name="nfc_settings">Поставке</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-sv/strings.xml b/OpenKeychain/src/main/res/values-sv/strings.xml
index e74a2104f..93b833590 100644
--- a/OpenKeychain/src/main/res/values-sv/strings.xml
+++ b/OpenKeychain/src/main/res/values-sv/strings.xml
@@ -178,8 +178,7 @@
<string name="pin_for">Ange PIN för \'%s\'</string>
<string name="yubikey_pin_for">Ange PIN för att få åtkomst till YubiKey för \'%s\'</string>
<string name="nfc_text">Håll YubiKey mot baksidan av din enhet.</string>
- <string name="file_delete_confirmation">Vill du verkligen radera\n%s?</string>
- <string name="no_file_selected">Välj en fil först.</string>
+ <string name="no_file_selected">Välj en fil först.</string>
<string name="encrypt_sign_successful">Signerades och/eller krypterades.</string>
<string name="encrypt_sign_clipboard_successful">Signerades och/eller krypterades till urklipp.</string>
<string name="select_encryption_key">Välj åtminstone en krypteringsnyckel.</string>
@@ -864,4 +863,5 @@
<string name="no_nfc_support">Denna enhet stöder inte NFC</string>
<string name="unlocked">Upplåst</string>
<string name="nfc_settings">Inställningar</string>
+ <string name="file_delete_successful"></string>
</resources>
diff --git a/OpenKeychain/src/main/res/values-tr/strings.xml b/OpenKeychain/src/main/res/values-tr/strings.xml
index a5ab9ca63..2b60c9758 100644
--- a/OpenKeychain/src/main/res/values-tr/strings.xml
+++ b/OpenKeychain/src/main/res/values-tr/strings.xml
@@ -167,8 +167,7 @@
<string name="passphrase_for_symmetric_encryption">Simetrik şifreleme.</string>
<string name="passphrase_for">\'%s\' için bir parola girin</string>
<string name="nfc_text">YubiKey\'inizi cihazınızın arkasında tutun.</string>
- <string name="file_delete_confirmation">Silmek istediğinize emin misiniz\n%s?</string>
- <string name="no_file_selected">Önce bir dosya seçin.</string>
+ <string name="no_file_selected">Önce bir dosya seçin.</string>
<string name="encrypt_sign_successful">Başarıyla imzalandı ve/veya şifrelendi.</string>
<string name="encrypt_sign_clipboard_successful">Kopyalama önbelleğine başarıyla imzalandı ve/veya şifrelendi.</string>
<string name="select_encryption_key">En az bir şifreleme anahtarı seçiniz.</string>
@@ -509,7 +508,8 @@
<string name="error_multi_not_supported">Birden çok dosyanın kaydedilmesi desteklenmiyor. Bu şu anki Android\'in bir kısıtlamasıdır.</string>
<string name="key_colon">Anahtar:</string>
<string name="exchange_description">Anahtar değiş tokuşu başlatmak için sağ taraftan katılımcıların sayısını seçin ve \"Değiş tokuşu başlat\" tuşuna tıklayın.\n\nSadece istenilen katılımcıların değişim işleminde olduğundan ve parmak izlerinin doğruluğundan emin olmak için size iki soru daha sorulacak.</string>
- <!--Passphrase wizard-->
+ <string name="file_delete_successful"></string>
+ <!--Passphrase wizard-->
<!--TODO: rename all the things!-->
<!--<string name="enter_passphrase_twice">Enter passphrase twice</string>-->
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
diff --git a/OpenKeychain/src/main/res/values-uk/strings.xml b/OpenKeychain/src/main/res/values-uk/strings.xml
index ed5012edb..b3a161758 100644
--- a/OpenKeychain/src/main/res/values-uk/strings.xml
+++ b/OpenKeychain/src/main/res/values-uk/strings.xml
@@ -168,8 +168,7 @@
<string name="passphrase_must_not_be_empty">Будь ласка, введіть парольну фразу.</string>
<string name="passphrase_for_symmetric_encryption">Симетричне шифрування.</string>
<string name="passphrase_for">Введіть парольну фразу для \'%s\'</string>
- <string name="file_delete_confirmation">Ви справді хочете вилучити\n%s?</string>
- <string name="no_file_selected">Виберіть спершу файл.</string>
+ <string name="no_file_selected">Виберіть спершу файл.</string>
<string name="encrypt_sign_successful">Успішно підписано та/або перевірено.</string>
<string name="encrypt_sign_clipboard_successful">Успішно підписано та/або зашифровано до буфера обміну.</string>
<string name="select_encryption_key">Виберіть принаймні один ключ шифрування.</string>
@@ -589,7 +588,8 @@
<string name="can_sign_not">не можна підписати</string>
<string name="error_no_encrypt_subkey">Жодний підключ шифрування недоступний!</string>
<string name="contact_show_key">Показати ключ (%s)</string>
- <!--Passphrase wizard-->
+ <string name="file_delete_successful"></string>
+ <!--Passphrase wizard-->
<!--TODO: rename all the things!-->
<!--<string name="enter_passphrase_twice">Enter passphrase twice</string>-->
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
diff --git a/OpenKeychain/src/main/res/values-zh-rTW/strings.xml b/OpenKeychain/src/main/res/values-zh-rTW/strings.xml
index 9b6ef4c91..286e98b79 100644
--- a/OpenKeychain/src/main/res/values-zh-rTW/strings.xml
+++ b/OpenKeychain/src/main/res/values-zh-rTW/strings.xml
@@ -139,8 +139,7 @@
<string name="passphrases_do_not_match">口令不相符。</string>
<string name="passphrase_must_not_be_empty">請輸入口令。</string>
<string name="passphrase_for_symmetric_encryption">對稱加密。</string>
- <string name="file_delete_confirmation">你確定要刪除\n%s?</string>
- <string name="no_file_selected">請先選擇檔案。</string>
+ <string name="no_file_selected">請先選擇檔案。</string>
<string name="encrypt_sign_successful">成功簽名並/或加密。</string>
<string name="encrypt_sign_clipboard_successful">成功簽名並/或加密到剪貼簿。</string>
<string name="select_encryption_key">選擇至少一把加密金鑰。</string>
@@ -422,7 +421,8 @@
<string name="error_no_encrypt_subkey">沒有可供加密的子金鑰!</string>
<string name="info_no_manual_account_creation">請不要自行建立OpenKeychain帳戶。\n更多資訊請參考說明。</string>
<string name="exchange_description">要發起金鑰交換,先在右邊選擇與會人數,然後點選〝開始交換〞。\n\n接下來會詢問你兩個問題,以確保會議成員與交換的指紋是正確的。</string>
- <!--Passphrase wizard-->
+ <string name="file_delete_successful"></string>
+ <!--Passphrase wizard-->
<!--TODO: rename all the things!-->
<!--<string name="enter_passphrase_twice">Enter passphrase twice</string>-->
<!--<string name="nfc_text">Please place a NFC tag near your device</string>-->
diff --git a/OpenKeychain/src/main/res/values-zh/strings.xml b/OpenKeychain/src/main/res/values-zh/strings.xml
index a255362fb..d59b2a2e0 100644
--- a/OpenKeychain/src/main/res/values-zh/strings.xml
+++ b/OpenKeychain/src/main/res/values-zh/strings.xml
@@ -195,7 +195,9 @@
<string name="api_select_pub_keys_text">请重审收件人列表</string>
<!--Share-->
<string name="share_nfc_dialog">使用NFC分享</string>
- <!--Key list-->
+ <string name="file_delete_successful"></string>
+ <string name="file_delete_confirmation"></string>
+ <!--Key list-->
<!--Key view-->
<!--Key trust-->
<!--keybase proof stuff-->
diff --git a/OpenKeychain/src/main/res/values/strings.xml b/OpenKeychain/src/main/res/values/strings.xml
index 920fbf2a8..0affa9073 100644
--- a/OpenKeychain/src/main/res/values/strings.xml
+++ b/OpenKeychain/src/main/res/values/strings.xml
@@ -222,8 +222,9 @@
<string name="pin_for">"Enter PIN for '%s'"</string>
<string name="yubikey_pin_for">"Enter PIN to access YubiKey for '%s'"</string>
<string name="nfc_text">"Hold YubiKey against the back of your device."</string>
- <string name="file_delete_confirmation">"Are you sure you want to delete\n%s?"</string>
- <string name="file_delete_successful">"'%s' has been deleted."</string>
+ <string name="file_delete_confirmation_title">"Delete original files?"</string>
+ <string name="file_delete_confirmation">"The following files will be deleted:%s"</string>
+ <string name="file_delete_successful">"%1$d out of %2$d files have been deleted.%3$s"</string>
<string name="no_file_selected">"Select a file first."</string>
<string name="encrypt_sign_successful">"Successfully signed and/or encrypted."</string>
<string name="encrypt_sign_clipboard_successful">"Successfully signed and/or encrypted to clipboard."</string>
@@ -264,7 +265,8 @@
no punctuation, all lowercase,
they will be put after "error_message", e.g. "Error: file not found"
-->
- <string name="error_file_delete_failed">"Deleting '%s' failed. Please do this manually!"</string>
+ <string name="error_file_delete_failed">"have not been deleted. Delete them manually!"</string>
+ <string name="error_file_added_already">%s has already been added.</string>
<string name="error_file_not_found">"file not found"</string>
<string name="error_no_secret_key_found">"no suitable secret key found"</string>
<string name="error_external_storage_not_ready">"external storage not ready"</string>