-Improved email sanity verifications when adding emails when creating a new Key

-fixed a few NFC crashes
-fixed a few instances when showing the keyboard would crash the Activity
-fixed a case where adding new emails would crash the app if the user went back and forth between the Add Email fragment and the Add Name fragment.
This commit is contained in:
Daniel Ramos
2015-04-14 03:40:59 +01:00
parent a545d50f4b
commit d097131a3d
6 changed files with 82 additions and 30 deletions

View File

@@ -18,7 +18,6 @@
package org.sufficientlysecure.keychain.ui; package org.sufficientlysecure.keychain.ui;
import android.app.Activity; import android.app.Activity;
import android.content.Context;
import android.os.Bundle; import android.os.Bundle;
import android.os.Handler; import android.os.Handler;
import android.os.Message; import android.os.Message;
@@ -27,6 +26,7 @@ import android.support.v4.app.Fragment;
import android.support.v7.widget.DefaultItemAnimator; import android.support.v7.widget.DefaultItemAnimator;
import android.support.v7.widget.LinearLayoutManager; import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView; import android.support.v7.widget.RecyclerView;
import android.util.Patterns;
import android.view.LayoutInflater; import android.view.LayoutInflater;
import android.view.View; import android.view.View;
import android.view.ViewGroup; import android.view.ViewGroup;
@@ -44,6 +44,7 @@ import org.sufficientlysecure.keychain.ui.widget.EmailEditText;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.regex.Pattern;
public class CreateKeyEmailFragment extends Fragment { public class CreateKeyEmailFragment extends Fragment {
@@ -73,14 +74,13 @@ public class CreateKeyEmailFragment extends Fragment {
* Checks if text of given EditText is not empty. If it is empty an error is * Checks if text of given EditText is not empty. If it is empty an error is
* set and the EditText gets the focus. * set and the EditText gets the focus.
* *
* @param context
* @param editText * @param editText
* @return true if EditText is not empty * @return true if EditText is not empty
*/ */
private static boolean isEditTextNotEmpty(Context context, EditText editText) { private boolean isMainEmailValid(EditText editText) {
boolean output = true; boolean output = true;
if (editText.getText().length() == 0) { if (!checkEmail(editText.getText().toString(), false)) {
editText.setError(context.getString(R.string.create_key_empty)); editText.setError(getString(R.string.create_key_empty));
editText.requestFocus(); editText.requestFocus();
output = false; output = false;
} else { } else {
@@ -125,7 +125,7 @@ public class CreateKeyEmailFragment extends Fragment {
// initial values // initial values
if (mAdditionalEmailModels == null) { if (mAdditionalEmailModels == null) {
mAdditionalEmailModels = new ArrayList<>(); mAdditionalEmailModels = new ArrayList<>();
if (mCreateKeyActivity.mAdditionalEmails != null) { if (mCreateKeyActivity.mAdditionalEmails != null && mEmailAdapter != null) {
mEmailAdapter.addAll(mCreateKeyActivity.mAdditionalEmails); mEmailAdapter.addAll(mCreateKeyActivity.mAdditionalEmails);
} }
} }
@@ -144,6 +144,65 @@ public class CreateKeyEmailFragment extends Fragment {
return view; return view;
} }
/**
* Checks if a given email is valid
*
* @param email
* @param additionalEmail
* @return
*/
private boolean checkEmail(String email, boolean additionalEmail) {
//check for email format or if the user did any input
if (!isEmailFormatValid(email)) {
Notify.create(getActivity(),
getString(R.string.create_key_email_invalid_email),
Notify.LENGTH_LONG, Notify.Style.ERROR).show();
return false;
}
//check for duplicated emails
if (!additionalEmail && isEmailDuplicatedInsideAdapter(email) || additionalEmail &&
mEmailEdit.getText().length() > 0 && email.equals(mEmailEdit.getText().toString())) {
Notify.create(getActivity(),
getString(R.string.create_key_email_already_exists_text),
Notify.LENGTH_LONG, Notify.Style.ERROR).show();
return false;
}
return true;
}
/**
* Checks the email format
* Uses the default Android Email Pattern
*
* @param email
* @return
*/
private boolean isEmailFormatValid(String email) {
Pattern emailPattern = Patterns.EMAIL_ADDRESS;
//check for email format or if the user did any input
return !(email.length() == 0 || !emailPattern.matcher(email).matches());
}
/**
* Checks for duplicated emails inside the additional email adapter.
*
* @param email
* @return
*/
private boolean isEmailDuplicatedInsideAdapter(String email) {
//check for duplicated emails inside the adapter
for (EmailAdapter.ViewModel model : mAdditionalEmailModels) {
if (email.equals(model.email)) {
return true;
}
}
return false;
}
private void addEmail() { private void addEmail() {
Handler returnHandler = new Handler() { Handler returnHandler = new Handler() {
@Override @Override
@@ -152,26 +211,10 @@ public class CreateKeyEmailFragment extends Fragment {
Bundle data = message.getData(); Bundle data = message.getData();
String email = data.getString(AddEmailDialogFragment.MESSAGE_DATA_EMAIL); String email = data.getString(AddEmailDialogFragment.MESSAGE_DATA_EMAIL);
if (checkEmail(email, true)) {
if (email.length() > 0 && mEmailEdit.getText().length() > 0 && // add new user id
email.equals(mEmailEdit.getText().toString())) { mEmailAdapter.add(email);
Notify.create(getActivity(),
getString(R.string.create_key_email_already_exists_text),
Notify.LENGTH_LONG, Notify.Style.ERROR).show();
return;
} }
//check for duplicated emails inside the adapter
for (EmailAdapter.ViewModel model : mAdditionalEmailModels) {
if (email.equals(model.email)) {
Notify.create(getActivity(),
getString(R.string.create_key_email_already_exists_text),
Notify.LENGTH_LONG, Notify.Style.ERROR).show();
return;
}
}
// add new user id
mEmailAdapter.add(email);
} }
} }
}; };
@@ -191,7 +234,7 @@ public class CreateKeyEmailFragment extends Fragment {
} }
private void nextClicked() { private void nextClicked() {
if (isEditTextNotEmpty(getActivity(), mEmailEdit)) { if (isMainEmailValid(mEmailEdit)) {
// save state // save state
mCreateKeyActivity.mEmail = mEmailEdit.getText().toString(); mCreateKeyActivity.mEmail = mEmailEdit.getText().toString();
mCreateKeyActivity.mAdditionalEmails = getAdditionalEmails(); mCreateKeyActivity.mAdditionalEmails = getAdditionalEmails();

View File

@@ -451,6 +451,8 @@ public abstract class BaseNfcActivity extends BaseActivity {
*/ */
public void enableNfcForegroundDispatch() { public void enableNfcForegroundDispatch() {
mNfcAdapter = NfcAdapter.getDefaultAdapter(this); mNfcAdapter = NfcAdapter.getDefaultAdapter(this);
if(mNfcAdapter == null) return;
Intent nfcI = new Intent(this, getClass()) Intent nfcI = new Intent(this, getClass())
.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_CLEAR_TOP); .addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent nfcPendingIntent = PendingIntent.getActivity(this, 0, nfcI, PendingIntent.FLAG_CANCEL_CURRENT); PendingIntent nfcPendingIntent = PendingIntent.getActivity(this, 0, nfcI, PendingIntent.FLAG_CANCEL_CURRENT);
@@ -472,7 +474,9 @@ public abstract class BaseNfcActivity extends BaseActivity {
* Disable foreground dispatch in onPause! * Disable foreground dispatch in onPause!
*/ */
public void disableNfcForegroundDispatch() { public void disableNfcForegroundDispatch() {
mNfcAdapter.disableForegroundDispatch(this); if(mNfcAdapter != null) {
mNfcAdapter.disableForegroundDispatch(this);
}
Log.d(Constants.TAG, "NfcForegroundDispatch has been disabled!"); Log.d(Constants.TAG, "NfcForegroundDispatch has been disabled!");
} }

View File

@@ -112,9 +112,11 @@ public class AddEmailDialogFragment extends DialogFragment implements OnEditorAc
mEmail.post(new Runnable() { mEmail.post(new Runnable() {
@Override @Override
public void run() { public void run() {
InputMethodManager imm = (InputMethodManager) getActivity() if(getActivity() != null) {
.getSystemService(Context.INPUT_METHOD_SERVICE); InputMethodManager imm = (InputMethodManager) getActivity()
imm.showSoftInput(mEmail, InputMethodManager.SHOW_IMPLICIT); .getSystemService(Context.INPUT_METHOD_SERVICE);
imm.showSoftInput(mEmail, InputMethodManager.SHOW_IMPLICIT);
}
} }
}); });
} }

View File

@@ -21,6 +21,7 @@
android:layout_marginTop="16dp" android:layout_marginTop="16dp"
android:hint="@string/label_email" android:hint="@string/label_email"
android:imeOptions="actionNext" android:imeOptions="actionNext"
android:inputType="textEmailAddress"
android:textAppearance="?android:attr/textAppearanceMedium" /> android:textAppearance="?android:attr/textAppearanceMedium" />
</LinearLayout> </LinearLayout>

View File

@@ -32,6 +32,7 @@
android:layout_marginTop="16dp" android:layout_marginTop="16dp"
android:layout_marginBottom="8dp" android:layout_marginBottom="8dp"
android:imeOptions="actionNext" android:imeOptions="actionNext"
android:inputType="textEmailAddress"
android:hint="@string/label_email" android:hint="@string/label_email"
android:ems="10" /> android:ems="10" />

View File

@@ -631,6 +631,7 @@
<string name="create_key_add_email">"Add email address"</string> <string name="create_key_add_email">"Add email address"</string>
<string name="create_key_add_email_text">"Additional email addresses are also associated to this key and can be used for secure communication."</string> <string name="create_key_add_email_text">"Additional email addresses are also associated to this key and can be used for secure communication."</string>
<string name="create_key_email_already_exists_text">"Email address has already been added"</string> <string name="create_key_email_already_exists_text">"Email address has already been added"</string>
<string name="create_key_email_invalid_email">"Email address format is invalid"</string>
<!-- View key --> <!-- View key -->
<string name="view_key_revoked">"Revoked: Key must not be used anymore!"</string> <string name="view_key_revoked">"Revoked: Key must not be used anymore!"</string>