Add a method for verifying that numbers are normalized in addition to being dialable
This commit is contained in:
parent
a3fe4b9980
commit
7762afc497
|
@ -0,0 +1,17 @@
|
|||
/*
|
||||
* Copyright 2013-2021 Signal Messenger, LLC
|
||||
* SPDX-License-Identifier: AGPL-3.0-only
|
||||
*/
|
||||
|
||||
package org.whispersystems.textsecuregcm.util;
|
||||
|
||||
public class ImpossibleNumberException extends Exception {
|
||||
|
||||
public ImpossibleNumberException() {
|
||||
super();
|
||||
}
|
||||
|
||||
public ImpossibleNumberException(final Throwable cause) {
|
||||
super(cause);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,25 @@
|
|||
/*
|
||||
* Copyright 2013-2021 Signal Messenger, LLC
|
||||
* SPDX-License-Identifier: AGPL-3.0-only
|
||||
*/
|
||||
|
||||
package org.whispersystems.textsecuregcm.util;
|
||||
|
||||
public class NonNormalizedNumberException extends Exception {
|
||||
|
||||
private final String originalNumber;
|
||||
private final String normalizedNumber;
|
||||
|
||||
public NonNormalizedNumberException(final String originalNumber, final String normalizedNumber) {
|
||||
this.originalNumber = originalNumber;
|
||||
this.normalizedNumber = normalizedNumber;
|
||||
}
|
||||
|
||||
public String getOriginalNumber() {
|
||||
return originalNumber;
|
||||
}
|
||||
|
||||
public String getNormalizedNumber() {
|
||||
return normalizedNumber;
|
||||
}
|
||||
}
|
|
@ -4,7 +4,10 @@
|
|||
*/
|
||||
package org.whispersystems.textsecuregcm.util;
|
||||
|
||||
import com.google.i18n.phonenumbers.NumberParseException;
|
||||
import com.google.i18n.phonenumbers.PhoneNumberUtil;
|
||||
import com.google.i18n.phonenumbers.PhoneNumberUtil.PhoneNumberFormat;
|
||||
import com.google.i18n.phonenumbers.Phonenumber.PhoneNumber;
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.URLEncoder;
|
||||
import java.security.MessageDigest;
|
||||
|
@ -28,6 +31,8 @@ public class Util {
|
|||
|
||||
private static final Pattern COUNTRY_CODE_PATTERN = Pattern.compile("^\\+([17]|2[07]|3[0123469]|4[013456789]|5[12345678]|6[0123456]|8[1246]|9[0123458]|\\d{3})");
|
||||
|
||||
private static final PhoneNumberUtil PHONE_NUMBER_UTIL = PhoneNumberUtil.getInstance();
|
||||
|
||||
public static byte[] getContactToken(String number) {
|
||||
try {
|
||||
MessageDigest digest = MessageDigest.getInstance("SHA1");
|
||||
|
@ -41,7 +46,32 @@ public class Util {
|
|||
}
|
||||
|
||||
public static boolean isValidNumber(String number) {
|
||||
return number.matches("^\\+[0-9]+") && PhoneNumberUtil.getInstance().isPossibleNumber(number, null);
|
||||
return number.matches("^\\+[0-9]+") && PHONE_NUMBER_UTIL.isPossibleNumber(number, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks that the given number is a valid, E164-normalized phone number.
|
||||
*
|
||||
* @param number the number to check
|
||||
*
|
||||
* @throws ImpossibleNumberException if the given number is not a valid phone number at all
|
||||
* @throws NonNormalizedNumberException if the given number is a valid phone number, but isn't E164-normalized
|
||||
*/
|
||||
public static void requireNormalizedNumber(final String number) throws ImpossibleNumberException, NonNormalizedNumberException {
|
||||
if (!PHONE_NUMBER_UTIL.isPossibleNumber(number, null)) {
|
||||
throw new ImpossibleNumberException();
|
||||
}
|
||||
|
||||
try {
|
||||
final PhoneNumber phoneNumber = PHONE_NUMBER_UTIL.parse(number, null);
|
||||
final String normalizedNumber = PHONE_NUMBER_UTIL.format(phoneNumber, PhoneNumberFormat.E164);
|
||||
|
||||
if (!number.equals(normalizedNumber)) {
|
||||
throw new NonNormalizedNumberException(number, normalizedNumber);
|
||||
}
|
||||
} catch (final NumberParseException e) {
|
||||
throw new ImpossibleNumberException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public static String getCountryCode(String number) {
|
||||
|
|
|
@ -5,14 +5,20 @@
|
|||
|
||||
package org.whispersystems.textsecuregcm.tests.util;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.params.ParameterizedTest;
|
||||
import org.junit.jupiter.params.provider.Arguments;
|
||||
import org.junit.jupiter.params.provider.MethodSource;
|
||||
import org.junit.jupiter.params.provider.ValueSource;
|
||||
import org.whispersystems.textsecuregcm.util.ImpossibleNumberException;
|
||||
import org.whispersystems.textsecuregcm.util.NonNormalizedNumberException;
|
||||
import org.whispersystems.textsecuregcm.util.Util;
|
||||
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertThrows;
|
||||
|
||||
class ValidNumberTest {
|
||||
|
||||
|
@ -53,4 +59,51 @@ class ValidNumberTest {
|
|||
Arguments.of("+689123456", true)
|
||||
);
|
||||
}
|
||||
|
||||
@ParameterizedTest
|
||||
@ValueSource(strings = {
|
||||
"+447700900111",
|
||||
"+14151231234",
|
||||
"+71234567890",
|
||||
"+447535742222",
|
||||
"+4915174108888",
|
||||
"+298123456",
|
||||
"+299123456",
|
||||
"+376123456",
|
||||
"+68512345",
|
||||
"+689123456"})
|
||||
void requireNormalizedNumber(final String number) {
|
||||
assertDoesNotThrow(() -> Util.requireNormalizedNumber(number));
|
||||
}
|
||||
|
||||
@Test
|
||||
void requireNormalizedNumberNull() {
|
||||
assertThrows(ImpossibleNumberException.class, () -> Util.requireNormalizedNumber(null));
|
||||
}
|
||||
|
||||
@ParameterizedTest
|
||||
@ValueSource(strings = {
|
||||
"Definitely not a phone number at all",
|
||||
"+141512312341",
|
||||
"+712345678901",
|
||||
"+4475357422221",
|
||||
"+491517410888811111",
|
||||
"71234567890",
|
||||
"001447535742222",
|
||||
"+1415123123a"
|
||||
})
|
||||
void requireNormalizedNumberImpossibleNumber(final String number) {
|
||||
assertThrows(ImpossibleNumberException.class, () -> Util.requireNormalizedNumber(number));
|
||||
}
|
||||
|
||||
@ParameterizedTest
|
||||
@ValueSource(strings = {
|
||||
"+4407700900111",
|
||||
"+1 415 123 1234",
|
||||
"+1 (415) 123-1234",
|
||||
"+1 415)123-1234",
|
||||
" +14151231234"})
|
||||
void requireNormalizedNumberNonNormalized(final String number) {
|
||||
assertThrows(NonNormalizedNumberException.class, () -> Util.requireNormalizedNumber(number));
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue