kopia lustrzana https://github.com/ryukoposting/Signal-Android
Fix race condition overriding profile on registration.
rodzic
e2cb522e87
commit
e687fea567
|
@ -7,6 +7,7 @@ import org.signal.core.util.logging.Log;
|
||||||
import org.thoughtcrime.securesms.jobmanager.Data;
|
import org.thoughtcrime.securesms.jobmanager.Data;
|
||||||
import org.thoughtcrime.securesms.jobmanager.Job;
|
import org.thoughtcrime.securesms.jobmanager.Job;
|
||||||
import org.thoughtcrime.securesms.jobmanager.impl.NetworkConstraint;
|
import org.thoughtcrime.securesms.jobmanager.impl.NetworkConstraint;
|
||||||
|
import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||||
import org.thoughtcrime.securesms.util.ProfileUtil;
|
import org.thoughtcrime.securesms.util.ProfileUtil;
|
||||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||||
|
|
||||||
|
@ -42,6 +43,7 @@ public final class ProfileUploadJob extends BaseJob {
|
||||||
}
|
}
|
||||||
|
|
||||||
ProfileUtil.uploadProfile(context);
|
ProfileUtil.uploadProfile(context);
|
||||||
|
SignalStore.registrationValues().markHasUploadedProfile();
|
||||||
Log.i(TAG, "Profile uploaded.");
|
Log.i(TAG, "Profile uploaded.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -15,6 +15,7 @@ import org.thoughtcrime.securesms.dependencies.ApplicationDependencies;
|
||||||
import org.thoughtcrime.securesms.jobmanager.Data;
|
import org.thoughtcrime.securesms.jobmanager.Data;
|
||||||
import org.thoughtcrime.securesms.jobmanager.Job;
|
import org.thoughtcrime.securesms.jobmanager.Job;
|
||||||
import org.thoughtcrime.securesms.jobmanager.impl.NetworkConstraint;
|
import org.thoughtcrime.securesms.jobmanager.impl.NetworkConstraint;
|
||||||
|
import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||||
import org.thoughtcrime.securesms.profiles.ProfileName;
|
import org.thoughtcrime.securesms.profiles.ProfileName;
|
||||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||||
import org.thoughtcrime.securesms.util.ProfileUtil;
|
import org.thoughtcrime.securesms.util.ProfileUtil;
|
||||||
|
@ -71,6 +72,16 @@ public class RefreshOwnProfileJob extends BaseJob {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (SignalStore.kbsValues().hasPin() && !SignalStore.kbsValues().hasOptedOut() && SignalStore.storageService().getLastSyncTime() == 0) {
|
||||||
|
Log.i(TAG, "Registered with PIN but haven't completed storage sync yet.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!SignalStore.registrationValues().hasUploadedProfile()) {
|
||||||
|
Log.i(TAG, "Registered but haven't uploaded profile yet.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
Recipient self = Recipient.self();
|
Recipient self = Recipient.self();
|
||||||
ProfileAndCredential profileAndCredential = ProfileUtil.retrieveProfileSync(context, self, getRequestType(self));
|
ProfileAndCredential profileAndCredential = ProfileUtil.retrieveProfileSync(context, self, getRequestType(self));
|
||||||
SignalServiceProfile profile = profileAndCredential.getProfile();
|
SignalServiceProfile profile = profileAndCredential.getProfile();
|
||||||
|
@ -113,6 +124,7 @@ public class RefreshOwnProfileJob extends BaseJob {
|
||||||
String plaintextName = ProfileUtil.decryptString(profileKey, encryptedName);
|
String plaintextName = ProfileUtil.decryptString(profileKey, encryptedName);
|
||||||
ProfileName profileName = ProfileName.fromSerialized(plaintextName);
|
ProfileName profileName = ProfileName.fromSerialized(plaintextName);
|
||||||
|
|
||||||
|
Log.d(TAG, "Saving " + (!Util.isEmpty(plaintextName) ? "non-" : "") + "empty name.");
|
||||||
DatabaseFactory.getRecipientDatabase(context).setProfileName(Recipient.self().getId(), profileName);
|
DatabaseFactory.getRecipientDatabase(context).setProfileName(Recipient.self().getId(), profileName);
|
||||||
} catch (InvalidCiphertextException | IOException e) {
|
} catch (InvalidCiphertextException | IOException e) {
|
||||||
Log.w(TAG, e);
|
Log.w(TAG, e);
|
||||||
|
@ -135,6 +147,7 @@ public class RefreshOwnProfileJob extends BaseJob {
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void setProfileAvatar(@Nullable String avatar) {
|
private static void setProfileAvatar(@Nullable String avatar) {
|
||||||
|
Log.d(TAG, "Saving " + (!Util.isEmpty(avatar) ? "non-" : "") + "empty avatar.");
|
||||||
ApplicationDependencies.getJobManager().add(new RetrieveProfileAvatarJob(Recipient.self(), avatar));
|
ApplicationDependencies.getJobManager().add(new RetrieveProfileAvatarJob(Recipient.self(), avatar));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -10,6 +10,7 @@ public final class RegistrationValues extends SignalStoreValues {
|
||||||
|
|
||||||
private static final String REGISTRATION_COMPLETE = "registration.complete";
|
private static final String REGISTRATION_COMPLETE = "registration.complete";
|
||||||
private static final String PIN_REQUIRED = "registration.pin_required";
|
private static final String PIN_REQUIRED = "registration.pin_required";
|
||||||
|
private static final String HAS_UPLOADED_PROFILE = "registration.has_uploaded_profile";
|
||||||
|
|
||||||
RegistrationValues(@NonNull KeyValueStore store) {
|
RegistrationValues(@NonNull KeyValueStore store) {
|
||||||
super(store);
|
super(store);
|
||||||
|
@ -46,4 +47,12 @@ public final class RegistrationValues extends SignalStoreValues {
|
||||||
public synchronized boolean isRegistrationComplete() {
|
public synchronized boolean isRegistrationComplete() {
|
||||||
return getStore().getBoolean(REGISTRATION_COMPLETE, true);
|
return getStore().getBoolean(REGISTRATION_COMPLETE, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean hasUploadedProfile() {
|
||||||
|
return getBoolean(HAS_UPLOADED_PROFILE, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void markHasUploadedProfile() {
|
||||||
|
putBoolean(HAS_UPLOADED_PROFILE, true);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -165,8 +165,8 @@ public final class RegistrationRepository {
|
||||||
System.currentTimeMillis(),
|
System.currentTimeMillis(),
|
||||||
true);
|
true);
|
||||||
|
|
||||||
TextSecurePreferences.setPushRegistered(context, true);
|
|
||||||
TextSecurePreferences.setPushServerPassword(context, registrationData.getPassword());
|
TextSecurePreferences.setPushServerPassword(context, registrationData.getPassword());
|
||||||
|
TextSecurePreferences.setPushRegistered(context, true);
|
||||||
TextSecurePreferences.setSignedPreKeyRegistered(context, true);
|
TextSecurePreferences.setSignedPreKeyRegistered(context, true);
|
||||||
TextSecurePreferences.setPromptedPushRegistration(context, true);
|
TextSecurePreferences.setPromptedPushRegistration(context, true);
|
||||||
TextSecurePreferences.setUnauthorizedReceived(context, false);
|
TextSecurePreferences.setUnauthorizedReceived(context, false);
|
||||||
|
|
|
@ -9,23 +9,34 @@ import android.view.ViewGroup;
|
||||||
import androidx.annotation.NonNull;
|
import androidx.annotation.NonNull;
|
||||||
import androidx.annotation.Nullable;
|
import androidx.annotation.Nullable;
|
||||||
import androidx.fragment.app.FragmentActivity;
|
import androidx.fragment.app.FragmentActivity;
|
||||||
import androidx.lifecycle.ViewModelProviders;
|
import androidx.lifecycle.ViewModelProvider;
|
||||||
import androidx.navigation.ActivityNavigator;
|
import androidx.navigation.ActivityNavigator;
|
||||||
|
|
||||||
|
import org.signal.core.util.logging.Log;
|
||||||
import org.thoughtcrime.securesms.LoggingFragment;
|
import org.thoughtcrime.securesms.LoggingFragment;
|
||||||
import org.thoughtcrime.securesms.MainActivity;
|
import org.thoughtcrime.securesms.MainActivity;
|
||||||
import org.thoughtcrime.securesms.R;
|
import org.thoughtcrime.securesms.R;
|
||||||
|
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies;
|
||||||
|
import org.thoughtcrime.securesms.jobs.MultiDeviceProfileContentUpdateJob;
|
||||||
|
import org.thoughtcrime.securesms.jobs.MultiDeviceProfileKeyUpdateJob;
|
||||||
|
import org.thoughtcrime.securesms.jobs.ProfileUploadJob;
|
||||||
import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
import org.thoughtcrime.securesms.keyvalue.SignalStore;
|
||||||
import org.thoughtcrime.securesms.lock.v2.CreateKbsPinActivity;
|
import org.thoughtcrime.securesms.lock.v2.CreateKbsPinActivity;
|
||||||
import org.thoughtcrime.securesms.pin.PinRestoreActivity;
|
import org.thoughtcrime.securesms.pin.PinRestoreActivity;
|
||||||
|
import org.thoughtcrime.securesms.profiles.AvatarHelper;
|
||||||
import org.thoughtcrime.securesms.profiles.edit.EditProfileActivity;
|
import org.thoughtcrime.securesms.profiles.edit.EditProfileActivity;
|
||||||
|
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||||
|
import org.thoughtcrime.securesms.registration.RegistrationUtil;
|
||||||
import org.thoughtcrime.securesms.registration.viewmodel.RegistrationViewModel;
|
import org.thoughtcrime.securesms.registration.viewmodel.RegistrationViewModel;
|
||||||
|
|
||||||
|
import java.util.Arrays;
|
||||||
|
|
||||||
public final class RegistrationCompleteFragment extends LoggingFragment {
|
public final class RegistrationCompleteFragment extends LoggingFragment {
|
||||||
|
|
||||||
|
private static final String TAG = Log.tag(RegistrationCompleteFragment.class);
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
|
||||||
Bundle savedInstanceState) {
|
|
||||||
return inflater.inflate(R.layout.fragment_registration_blank, container, false);
|
return inflater.inflate(R.layout.fragment_registration_blank, container, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -34,24 +45,48 @@ public final class RegistrationCompleteFragment extends LoggingFragment {
|
||||||
super.onViewCreated(view, savedInstanceState);
|
super.onViewCreated(view, savedInstanceState);
|
||||||
|
|
||||||
FragmentActivity activity = requireActivity();
|
FragmentActivity activity = requireActivity();
|
||||||
RegistrationViewModel viewModel = ViewModelProviders.of(activity).get(RegistrationViewModel.class);
|
RegistrationViewModel viewModel = new ViewModelProvider(activity).get(RegistrationViewModel.class);
|
||||||
|
|
||||||
if (SignalStore.storageService().needsAccountRestore()) {
|
if (SignalStore.storageService().needsAccountRestore()) {
|
||||||
|
Log.i(TAG, "Performing pin restore");
|
||||||
activity.startActivity(new Intent(activity, PinRestoreActivity.class));
|
activity.startActivity(new Intent(activity, PinRestoreActivity.class));
|
||||||
} else if (!viewModel.isReregister()) {
|
} else if (!viewModel.isReregister()) {
|
||||||
final Intent main = MainActivity.clearTop(activity);
|
boolean needsProfile = Recipient.self().getProfileName().isEmpty() || !AvatarHelper.hasAvatar(activity, Recipient.self().getId());
|
||||||
final Intent profile = EditProfileActivity.getIntentForUserProfile(activity);
|
boolean needsPin = !SignalStore.kbsValues().hasPin();
|
||||||
|
|
||||||
Intent kbs = CreateKbsPinActivity.getIntentForPinCreate(requireContext());
|
Log.i(TAG, "Pin restore flow not required." +
|
||||||
activity.startActivity(chainIntents(chainIntents(profile, kbs), main));
|
" profile name: " + Recipient.self().getProfileName().isEmpty() +
|
||||||
|
" profile avatar: " + !AvatarHelper.hasAvatar(activity, Recipient.self().getId()) +
|
||||||
|
" needsPin:" + needsPin);
|
||||||
|
|
||||||
|
Intent startIntent = MainActivity.clearTop(activity);
|
||||||
|
|
||||||
|
if (needsPin) {
|
||||||
|
startIntent = chainIntents(CreateKbsPinActivity.getIntentForPinCreate(requireContext()), startIntent);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (needsProfile) {
|
||||||
|
startIntent = chainIntents(EditProfileActivity.getIntentForUserProfile(activity), startIntent);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!needsProfile && !needsPin) {
|
||||||
|
ApplicationDependencies.getJobManager()
|
||||||
|
.startChain(new ProfileUploadJob())
|
||||||
|
.then(Arrays.asList(new MultiDeviceProfileKeyUpdateJob(), new MultiDeviceProfileContentUpdateJob()))
|
||||||
|
.enqueue();
|
||||||
|
|
||||||
|
RegistrationUtil.maybeMarkRegistrationComplete(requireContext());
|
||||||
|
}
|
||||||
|
|
||||||
|
activity.startActivity(startIntent);
|
||||||
}
|
}
|
||||||
|
|
||||||
activity.finish();
|
activity.finish();
|
||||||
ActivityNavigator.applyPopAnimationsToPendingTransition(activity);
|
ActivityNavigator.applyPopAnimationsToPendingTransition(activity);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static Intent chainIntents(@NonNull Intent sourceIntent, @Nullable Intent nextIntent) {
|
private static @NonNull Intent chainIntents(@NonNull Intent sourceIntent, @NonNull Intent nextIntent) {
|
||||||
if (nextIntent != null) sourceIntent.putExtra("next_intent", nextIntent);
|
sourceIntent.putExtra("next_intent", nextIntent);
|
||||||
return sourceIntent;
|
return sourceIntent;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -229,6 +229,7 @@ public final class ProfileUtil {
|
||||||
Log.d(TAG, "Uploading " + (!Util.isEmpty(about) ? "non-" : "") + "empty about.");
|
Log.d(TAG, "Uploading " + (!Util.isEmpty(about) ? "non-" : "") + "empty about.");
|
||||||
Log.d(TAG, "Uploading " + (!Util.isEmpty(aboutEmoji) ? "non-" : "") + "empty emoji.");
|
Log.d(TAG, "Uploading " + (!Util.isEmpty(aboutEmoji) ? "non-" : "") + "empty emoji.");
|
||||||
Log.d(TAG, "Uploading " + (paymentsAddress != null ? "non-" : "") + "empty payments address.");
|
Log.d(TAG, "Uploading " + (paymentsAddress != null ? "non-" : "") + "empty payments address.");
|
||||||
|
Log.d(TAG, "Uploading " + (avatar != null && avatar.getLength() != 0 ? "non-" : "") + "empty avatar.");
|
||||||
|
|
||||||
ProfileKey profileKey = ProfileKeyUtil.getSelfProfileKey();
|
ProfileKey profileKey = ProfileKeyUtil.getSelfProfileKey();
|
||||||
SignalServiceAccountManager accountManager = ApplicationDependencies.getSignalServiceAccountManager();
|
SignalServiceAccountManager accountManager = ApplicationDependencies.getSignalServiceAccountManager();
|
||||||
|
|
Ładowanie…
Reference in New Issue