Add support for signal.me links.

fork-5.53.8
Greyson Parrelli 2021-07-28 11:58:03 -04:00 zatwierdzone przez GitHub
rodzic 138b7ea796
commit 3cc2cd0b17
Nie znaleziono w bazie danych klucza dla tego podpisu
ID klucza GPG: 4AEE18F83AFDEB23
5 zmienionych plików z 150 dodań i 0 usunięć

Wyświetl plik

@ -275,6 +275,16 @@
<data android:scheme="sgnl"
android:host="signal.tube" />
</intent-filter>
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="https"
android:host="signal.me" />
<data android:scheme="sgnl"
android:host="signal.me" />
</intent-filter>
</activity>
<activity android:name=".conversation.ConversationActivity"

Wyświetl plik

@ -49,6 +49,7 @@ public class MainActivity extends PassphraseRequiredActivity implements VoiceNot
handleGroupLinkInIntent(getIntent());
handleProxyInIntent(getIntent());
handleSignalMeIntent(getIntent());
CachedInflater.from(this).clear();
}
@ -65,6 +66,7 @@ public class MainActivity extends PassphraseRequiredActivity implements VoiceNot
super.onNewIntent(intent);
handleGroupLinkInIntent(intent);
handleProxyInIntent(intent);
handleSignalMeIntent(intent);
}
@Override
@ -115,6 +117,13 @@ public class MainActivity extends PassphraseRequiredActivity implements VoiceNot
}
}
private void handleSignalMeIntent(Intent intent) {
Uri data = intent.getData();
if (data != null) {
CommunicationActions.handlePotentialSignalMeUrl(this, data.toString());
}
}
@Override
public @NonNull VoiceNoteMediaController getVoiceNoteMediaController() {
return mediaController;

Wyświetl plik

@ -24,6 +24,7 @@ import org.signal.core.util.concurrent.SignalExecutors;
import org.signal.core.util.logging.Log;
import org.thoughtcrime.securesms.R;
import org.thoughtcrime.securesms.WebRtcCallActivity;
import org.thoughtcrime.securesms.contacts.sync.DirectoryHelper;
import org.thoughtcrime.securesms.conversation.ConversationIntents;
import org.thoughtcrime.securesms.database.DatabaseFactory;
import org.thoughtcrime.securesms.database.GroupDatabase;
@ -37,6 +38,9 @@ import org.thoughtcrime.securesms.proxy.ProxyBottomSheetFragment;
import org.thoughtcrime.securesms.recipients.Recipient;
import org.thoughtcrime.securesms.sms.MessageSender;
import org.thoughtcrime.securesms.util.concurrent.SimpleTask;
import org.thoughtcrime.securesms.util.views.SimpleProgressDialog;
import java.io.IOException;
public class CommunicationActions {
@ -225,6 +229,40 @@ public class CommunicationActions {
}
}
/**
* If the url is a proxy link it will handle it.
* Otherwise returns false, indicating was not a proxy link.
*/
public static boolean handlePotentialSignalMeUrl(@NonNull FragmentActivity activity, @NonNull String potentialUrl) {
String e164 = SignalMeUtil.parseE164FromLink(activity, potentialUrl);
if (e164 != null) {
SimpleProgressDialog.DismissibleDialog dialog = SimpleProgressDialog.showDelayed(activity, 500, 500);
SimpleTask.run(() -> {
Recipient recipient = Recipient.external(activity, e164);
if (!recipient.isRegistered() || !recipient.hasUuid()) {
try {
DirectoryHelper.refreshDirectoryFor(activity, recipient, false);
recipient = Recipient.resolved(recipient.getId());
} catch (IOException e) {
Log.w(TAG, "[handlePotentialMeUrl] Failed to refresh directory for new contact.");
}
}
return recipient;
}, recipient -> {
dialog.dismiss();
startConversation(activity, recipient, null);
});
return true;
} else {
return false;
}
}
private static void startInsecureCallInternal(@NonNull Activity activity, @NonNull Recipient recipient) {
try {
Intent dialIntent = new Intent(Intent.ACTION_DIAL, Uri.parse("tel:" + recipient.requireSmsAddress()));

Wyświetl plik

@ -0,0 +1,43 @@
package org.thoughtcrime.securesms.util;
import android.content.Context;
import android.telephony.PhoneNumberUtils;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import com.google.i18n.phonenumbers.PhoneNumberUtil;
import org.thoughtcrime.securesms.phonenumbers.PhoneNumberFormatter;
import java.util.Locale;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
class SignalMeUtil {
private static final String HOST = "signal.me";
private static final Pattern HOST_PATTERN = Pattern.compile("^(https|sgnl)://" + HOST + "/#p/(\\+[0-9]+)$");
/**
* If this is a valid signal.me link and has a valid e164, it will return the e164. Otherwise, it will return null.
*/
public static @Nullable String parseE164FromLink(@NonNull Context context, @Nullable String link) {
if (Util.isEmpty(link)) {
return null;
}
Matcher matcher = HOST_PATTERN.matcher(link);
if (matcher.matches()) {
String e164 = matcher.group(2);
if (PhoneNumberUtil.getInstance().isPossibleNumber(e164, Locale.getDefault().getCountry())) {
return PhoneNumberFormatter.get(context).format(e164);
} else {
return null;
}
} else {
return null;
}
}
}

Wyświetl plik

@ -0,0 +1,50 @@
package org.thoughtcrime.securesms.util;
import android.app.Application;
import androidx.test.core.app.ApplicationProvider;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.robolectric.ParameterizedRobolectricTestRunner;
import org.robolectric.annotation.Config;
import java.util.Arrays;
import java.util.Collection;
import static junit.framework.TestCase.assertEquals;
@RunWith(ParameterizedRobolectricTestRunner.class)
@Config(manifest = Config.NONE, application = Application.class)
public class SignalMeUtilText_parseE164FromLink {
private final String input;
private final String output;
@ParameterizedRobolectricTestRunner.Parameters
public static Collection<Object[]> data() {
return Arrays.asList(new Object[][]{
{ "https://signal.me/#p/+15555555555", "+15555555555" },
{ "https://signal.me/#p/5555555555", null },
{ "https://signal.me", null },
{ "https://signal.me/#p/", null },
{ "signal.me/#p/+15555555555", null },
{ "sgnl://signal.me/#p/+15555555555", "+15555555555" },
{ "sgnl://signal.me/#p/5555555555", null },
{ "sgnl://signal.me", null },
{ "sgnl://signal.me/#p/", null },
{ "", null },
{ null, null }
});
}
public SignalMeUtilText_parseE164FromLink(String input, String output) {
this.input = input;
this.output = output;
}
@Test
public void parse() {
assertEquals(output, SignalMeUtil.parseE164FromLink(ApplicationProvider.getApplicationContext(), input));
}
}