mirror of
https://github.com/signalapp/Signal-Android.git
synced 2026-04-21 17:29:32 +01:00
Blur avatar photos from unknown senders when in message request state.
This commit is contained in:
@@ -15,11 +15,9 @@ import com.google.protobuf.InvalidProtocolBufferException;
|
||||
|
||||
import org.signal.core.util.logging.Log;
|
||||
import org.signal.storageservice.protos.groups.AccessControl;
|
||||
import org.signal.storageservice.protos.groups.GroupChange;
|
||||
import org.signal.storageservice.protos.groups.Member;
|
||||
import org.signal.storageservice.protos.groups.local.DecryptedGroup;
|
||||
import org.signal.storageservice.protos.groups.local.DecryptedGroupChange;
|
||||
import org.signal.storageservice.protos.groups.local.DecryptedMember;
|
||||
import org.signal.zkgroup.InvalidInputException;
|
||||
import org.signal.zkgroup.groups.GroupMasterKey;
|
||||
import org.thoughtcrime.securesms.database.helpers.SQLCipherOpenHelper;
|
||||
@@ -447,15 +445,17 @@ public final class GroupDatabase extends Database {
|
||||
|
||||
contentValues.put(MMS, groupId.isMms());
|
||||
|
||||
List<RecipientId> groupMembers = members;
|
||||
if (groupMasterKey != null) {
|
||||
if (groupState == null) {
|
||||
throw new AssertionError("V2 master key but no group state");
|
||||
}
|
||||
groupId.requireV2();
|
||||
groupMembers = getV2GroupMembers(groupState);
|
||||
contentValues.put(V2_MASTER_KEY, groupMasterKey.serialize());
|
||||
contentValues.put(V2_REVISION, groupState.getRevision());
|
||||
contentValues.put(V2_DECRYPTED_GROUP, groupState.toByteArray());
|
||||
contentValues.put(MEMBERS, serializeV2GroupMembers(groupState));
|
||||
contentValues.put(MEMBERS, RecipientId.toSerializedList(groupMembers));
|
||||
} else {
|
||||
if (groupId.isV2()) {
|
||||
throw new AssertionError("V2 group id but no master key");
|
||||
@@ -468,6 +468,10 @@ public final class GroupDatabase extends Database {
|
||||
recipientDatabase.setExpireMessages(groupRecipientId, groupState.getDisappearingMessagesTimer().getDuration());
|
||||
}
|
||||
|
||||
if (groupMembers != null && (groupId.isMms() || Recipient.resolved(groupRecipientId).isProfileSharing())) {
|
||||
recipientDatabase.setHasGroupsInCommon(groupMembers);
|
||||
}
|
||||
|
||||
Recipient.live(groupRecipientId).refresh();
|
||||
|
||||
notifyConversationListListeners();
|
||||
@@ -585,10 +589,11 @@ public final class GroupDatabase extends Database {
|
||||
contentValues.put(UNMIGRATED_V1_MEMBERS, unmigratedV1Members.isEmpty() ? null : RecipientId.toSerializedList(unmigratedV1Members));
|
||||
}
|
||||
|
||||
List<RecipientId> groupMembers = getV2GroupMembers(decryptedGroup);
|
||||
contentValues.put(TITLE, title);
|
||||
contentValues.put(V2_REVISION, decryptedGroup.getRevision());
|
||||
contentValues.put(V2_DECRYPTED_GROUP, decryptedGroup.toByteArray());
|
||||
contentValues.put(MEMBERS, serializeV2GroupMembers(decryptedGroup));
|
||||
contentValues.put(MEMBERS, RecipientId.toSerializedList(groupMembers));
|
||||
contentValues.put(ACTIVE, gv2GroupActive(decryptedGroup) ? 1 : 0);
|
||||
|
||||
databaseHelper.getWritableDatabase().update(TABLE_NAME, contentValues,
|
||||
@@ -599,6 +604,10 @@ public final class GroupDatabase extends Database {
|
||||
recipientDatabase.setExpireMessages(groupRecipientId, decryptedGroup.getDisappearingMessagesTimer().getDuration());
|
||||
}
|
||||
|
||||
if (groupMembers != null && (groupId.isMms() || Recipient.resolved(groupRecipientId).isProfileSharing())) {
|
||||
recipientDatabase.setHasGroupsInCommon(groupMembers);
|
||||
}
|
||||
|
||||
Recipient.live(groupRecipientId).refresh();
|
||||
|
||||
notifyConversationListListeners();
|
||||
@@ -742,11 +751,11 @@ public final class GroupDatabase extends Database {
|
||||
return groupMembers;
|
||||
}
|
||||
|
||||
private static String serializeV2GroupMembers(@NonNull DecryptedGroup decryptedGroup) {
|
||||
private static List<RecipientId> getV2GroupMembers(@NonNull DecryptedGroup decryptedGroup) {
|
||||
List<UUID> uuids = DecryptedGroupUtil.membersToUuidList(decryptedGroup.getMembersList());
|
||||
List<RecipientId> recipientIds = uuidsToRecipientIds(uuids);
|
||||
|
||||
return RecipientId.toSerializedList(recipientIds);
|
||||
return recipientIds;
|
||||
}
|
||||
|
||||
public @NonNull List<GroupId.V2> getAllGroupV2Ids() {
|
||||
|
||||
@@ -8,6 +8,7 @@ import android.text.TextUtils;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.arch.core.util.Function;
|
||||
|
||||
import com.annimon.stream.Stream;
|
||||
import com.google.protobuf.ByteString;
|
||||
@@ -31,6 +32,7 @@ import org.thoughtcrime.securesms.database.helpers.SQLCipherOpenHelper;
|
||||
import org.thoughtcrime.securesms.database.model.ThreadRecord;
|
||||
import org.thoughtcrime.securesms.database.model.databaseprotos.DeviceLastResetTime;
|
||||
import org.thoughtcrime.securesms.database.model.databaseprotos.ProfileKeyCredentialColumnData;
|
||||
import org.thoughtcrime.securesms.database.model.databaseprotos.RecipientExtras;
|
||||
import org.thoughtcrime.securesms.database.model.databaseprotos.Wallpaper;
|
||||
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies;
|
||||
import org.thoughtcrime.securesms.groups.GroupId;
|
||||
@@ -43,8 +45,8 @@ import org.thoughtcrime.securesms.profiles.AvatarHelper;
|
||||
import org.thoughtcrime.securesms.profiles.ProfileName;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.recipients.RecipientId;
|
||||
import org.thoughtcrime.securesms.storage.StorageSyncHelper;
|
||||
import org.thoughtcrime.securesms.storage.StorageRecordUpdate;
|
||||
import org.thoughtcrime.securesms.storage.StorageSyncHelper;
|
||||
import org.thoughtcrime.securesms.storage.StorageSyncModels;
|
||||
import org.thoughtcrime.securesms.util.Base64;
|
||||
import org.thoughtcrime.securesms.util.Bitmask;
|
||||
@@ -68,8 +70,6 @@ import org.whispersystems.signalservice.api.storage.SignalAccountRecord;
|
||||
import org.whispersystems.signalservice.api.storage.SignalContactRecord;
|
||||
import org.whispersystems.signalservice.api.storage.SignalGroupV1Record;
|
||||
import org.whispersystems.signalservice.api.storage.SignalGroupV2Record;
|
||||
import org.whispersystems.signalservice.api.storage.SignalRecord;
|
||||
import org.whispersystems.signalservice.api.storage.SignalStorageRecord;
|
||||
import org.whispersystems.signalservice.api.storage.StorageId;
|
||||
import org.whispersystems.signalservice.api.util.UuidUtil;
|
||||
|
||||
@@ -142,8 +142,10 @@ public class RecipientDatabase extends Database {
|
||||
private static final String LAST_SESSION_RESET = "last_session_reset";
|
||||
private static final String WALLPAPER = "wallpaper";
|
||||
private static final String WALLPAPER_URI = "wallpaper_file";
|
||||
public static final String ABOUT = "about";
|
||||
public static final String ABOUT_EMOJI = "about_emoji";
|
||||
public static final String ABOUT = "about";
|
||||
public static final String ABOUT_EMOJI = "about_emoji";
|
||||
private static final String EXTRAS = "extras";
|
||||
private static final String GROUPS_IN_COMMON = "groups_in_common";
|
||||
|
||||
public static final String SEARCH_PROFILE_NAME = "search_signal_profile";
|
||||
private static final String SORT_NAME = "sort_name";
|
||||
@@ -170,12 +172,13 @@ public class RecipientDatabase extends Database {
|
||||
STORAGE_SERVICE_ID, DIRTY,
|
||||
MENTION_SETTING, WALLPAPER, WALLPAPER_URI,
|
||||
MENTION_SETTING,
|
||||
ABOUT, ABOUT_EMOJI
|
||||
ABOUT, ABOUT_EMOJI,
|
||||
EXTRAS, GROUPS_IN_COMMON
|
||||
};
|
||||
|
||||
private static final String[] ID_PROJECTION = new String[]{ID};
|
||||
private static final String[] SEARCH_PROJECTION = new String[]{ID, SYSTEM_JOINED_NAME, PHONE, EMAIL, SYSTEM_PHONE_LABEL, SYSTEM_PHONE_TYPE, REGISTERED, ABOUT, ABOUT_EMOJI, "COALESCE(" + nullIfEmpty(PROFILE_JOINED_NAME) + ", " + nullIfEmpty(PROFILE_GIVEN_NAME) + ") AS " + SEARCH_PROFILE_NAME, "COALESCE(" + nullIfEmpty(SYSTEM_JOINED_NAME) + ", " + nullIfEmpty(SYSTEM_GIVEN_NAME) + ", " + nullIfEmpty(PROFILE_JOINED_NAME) + ", " + nullIfEmpty(PROFILE_GIVEN_NAME) + ", " + nullIfEmpty(USERNAME) + ") AS " + SORT_NAME};
|
||||
public static final String[] SEARCH_PROJECTION_NAMES = new String[]{ID, SYSTEM_JOINED_NAME, PHONE, EMAIL, SYSTEM_PHONE_LABEL, SYSTEM_PHONE_TYPE, REGISTERED, ABOUT, ABOUT_EMOJI, SEARCH_PROFILE_NAME, SORT_NAME};
|
||||
private static final String[] SEARCH_PROJECTION = new String[]{ID, SYSTEM_JOINED_NAME, PHONE, EMAIL, SYSTEM_PHONE_LABEL, SYSTEM_PHONE_TYPE, REGISTERED, ABOUT, ABOUT_EMOJI, EXTRAS, GROUPS_IN_COMMON, "COALESCE(" + nullIfEmpty(PROFILE_JOINED_NAME) + ", " + nullIfEmpty(PROFILE_GIVEN_NAME) + ") AS " + SEARCH_PROFILE_NAME, "COALESCE(" + nullIfEmpty(SYSTEM_JOINED_NAME) + ", " + nullIfEmpty(SYSTEM_GIVEN_NAME) + ", " + nullIfEmpty(PROFILE_JOINED_NAME) + ", " + nullIfEmpty(PROFILE_GIVEN_NAME) + ", " + nullIfEmpty(USERNAME) + ") AS " + SORT_NAME};
|
||||
public static final String[] SEARCH_PROJECTION_NAMES = new String[]{ID, SYSTEM_JOINED_NAME, PHONE, EMAIL, SYSTEM_PHONE_LABEL, SYSTEM_PHONE_TYPE, REGISTERED, ABOUT, ABOUT_EMOJI, EXTRAS, GROUPS_IN_COMMON, SEARCH_PROFILE_NAME, SORT_NAME};
|
||||
private static final String[] TYPED_RECIPIENT_PROJECTION = Stream.of(RECIPIENT_PROJECTION)
|
||||
.map(columnName -> TABLE_NAME + "." + columnName)
|
||||
.toList().toArray(new String[0]);
|
||||
@@ -371,7 +374,9 @@ public class RecipientDatabase extends Database {
|
||||
WALLPAPER + " BLOB DEFAULT NULL, " +
|
||||
WALLPAPER_URI + " TEXT DEFAULT NULL, " +
|
||||
ABOUT + " TEXT DEFAULT NULL, " +
|
||||
ABOUT_EMOJI + " TEXT DEFAULT NULL);";
|
||||
ABOUT_EMOJI + " TEXT DEFAULT NULL, " +
|
||||
EXTRAS + " BLOB DEFAULT NULL, " +
|
||||
GROUPS_IN_COMMON + " INTEGER DEFAULT 0);";
|
||||
|
||||
private static final String INSIGHTS_INVITEE_LIST = "SELECT " + TABLE_NAME + "." + ID +
|
||||
" FROM " + TABLE_NAME +
|
||||
@@ -1461,6 +1466,7 @@ public class RecipientDatabase extends Database {
|
||||
byte[] wallpaper = CursorUtil.requireBlob(cursor, WALLPAPER);
|
||||
String about = CursorUtil.requireString(cursor, ABOUT);
|
||||
String aboutEmoji = CursorUtil.requireString(cursor, ABOUT_EMOJI);
|
||||
boolean hasGroupsInCommon = CursorUtil.requireBoolean(cursor, GROUPS_IN_COMMON);
|
||||
|
||||
MaterialColor color;
|
||||
byte[] profileKey = null;
|
||||
@@ -1549,7 +1555,9 @@ public class RecipientDatabase extends Database {
|
||||
chatWallpaper,
|
||||
about,
|
||||
aboutEmoji,
|
||||
getSyncExtras(cursor));
|
||||
getSyncExtras(cursor),
|
||||
getExtras(cursor),
|
||||
hasGroupsInCommon);
|
||||
}
|
||||
|
||||
private static @NonNull RecipientSettings.SyncExtras getSyncExtras(@NonNull Cursor cursor) {
|
||||
@@ -1565,6 +1573,23 @@ public class RecipientDatabase extends Database {
|
||||
return new RecipientSettings.SyncExtras(storageProto, groupMasterKey, identityKey, identityStatus, archived, forcedUnread);
|
||||
}
|
||||
|
||||
private static @Nullable Recipient.Extras getExtras(@NonNull Cursor cursor) {
|
||||
return Recipient.Extras.from(getRecipientExtras(cursor));
|
||||
}
|
||||
|
||||
private static @Nullable RecipientExtras getRecipientExtras(@NonNull Cursor cursor) {
|
||||
final Optional<byte[]> blob = CursorUtil.getBlob(cursor, EXTRAS);
|
||||
|
||||
return blob.transform(b -> {
|
||||
try {
|
||||
return RecipientExtras.parseFrom(b);
|
||||
} catch (InvalidProtocolBufferException e) {
|
||||
Log.w(TAG, e);
|
||||
throw new AssertionError(e);
|
||||
}
|
||||
}).orNull();
|
||||
}
|
||||
|
||||
public BulkOperationsHandle beginBulkSystemContactUpdate() {
|
||||
SQLiteDatabase database = databaseHelper.getWritableDatabase();
|
||||
database.beginTransaction();
|
||||
@@ -1986,6 +2011,14 @@ public class RecipientDatabase extends Database {
|
||||
boolean profiledUpdated = update(id, contentValues);
|
||||
boolean colorUpdated = enabled && setColorIfNotSetInternal(id, ContactColors.generateFor(Recipient.resolved(id).getDisplayName(context)));
|
||||
|
||||
if (profiledUpdated && enabled) {
|
||||
Optional<GroupDatabase.GroupRecord> group = DatabaseFactory.getGroupDatabase(context).getGroup(id);
|
||||
|
||||
if (group.isPresent()) {
|
||||
setHasGroupsInCommon(group.get().getMembers());
|
||||
}
|
||||
}
|
||||
|
||||
if (profiledUpdated || colorUpdated) {
|
||||
markDirty(id, DirtyState.UPDATE);
|
||||
Recipient.live(id).refresh();
|
||||
@@ -2841,6 +2874,93 @@ public class RecipientDatabase extends Database {
|
||||
}
|
||||
}
|
||||
|
||||
public void markPreMessageRequestRecipientsAsProfileSharingEnabled(long messageRequestEnableTime) {
|
||||
String[] whereArgs = SqlUtil.buildArgs(messageRequestEnableTime, messageRequestEnableTime);
|
||||
|
||||
String select = "SELECT r." + ID + " FROM " + TABLE_NAME + " AS r "
|
||||
+ "INNER JOIN " + ThreadDatabase.TABLE_NAME + " AS t ON t." + ThreadDatabase.RECIPIENT_ID + " = r." + ID + " WHERE "
|
||||
+ "r." + PROFILE_SHARING + " = 0 AND "
|
||||
+ "("
|
||||
+ "EXISTS(SELECT 1 FROM " + SmsDatabase.TABLE_NAME + " WHERE " + SmsDatabase.THREAD_ID + " = t." + ThreadDatabase.ID + " AND " + SmsDatabase.DATE_RECEIVED + " < ?) "
|
||||
+ "OR "
|
||||
+ "EXISTS(SELECT 1 FROM " + MmsDatabase.TABLE_NAME + " WHERE " + MmsDatabase.THREAD_ID + " = t." + ThreadDatabase.ID + " AND " + MmsDatabase.DATE_RECEIVED + " < ?) "
|
||||
+ ")";
|
||||
|
||||
List<Long> idsToUpdate = new ArrayList<>();
|
||||
try (Cursor cursor = databaseHelper.getReadableDatabase().rawQuery(select, whereArgs)) {
|
||||
while (cursor.moveToNext()) {
|
||||
idsToUpdate.add(CursorUtil.requireLong(cursor, ID));
|
||||
}
|
||||
}
|
||||
|
||||
if (Util.hasItems(idsToUpdate)) {
|
||||
SqlUtil.Query query = SqlUtil.buildCollectionQuery(ID, idsToUpdate);
|
||||
ContentValues values = new ContentValues(1);
|
||||
values.put(PROFILE_SHARING, 1);
|
||||
databaseHelper.getWritableDatabase().update(TABLE_NAME, values, query.getWhere(), query.getWhereArgs());
|
||||
|
||||
for (long id : idsToUpdate) {
|
||||
Recipient.live(RecipientId.from(id)).refresh();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void setHasGroupsInCommon(@NonNull List<RecipientId> recipientIds) {
|
||||
SqlUtil.Query query = SqlUtil.buildCollectionQuery(ID, recipientIds);
|
||||
SQLiteDatabase db = databaseHelper.getWritableDatabase();
|
||||
try (Cursor cursor = db.query(TABLE_NAME,
|
||||
new String[]{ID},
|
||||
query.getWhere() + " AND " + GROUPS_IN_COMMON + " = 0",
|
||||
query.getWhereArgs(),
|
||||
null,
|
||||
null,
|
||||
null))
|
||||
{
|
||||
List<Long> idsToUpdate = new ArrayList<>(cursor.getCount());
|
||||
while (cursor.moveToNext()) {
|
||||
idsToUpdate.add(CursorUtil.requireLong(cursor, ID));
|
||||
}
|
||||
|
||||
if (Util.hasItems(idsToUpdate)) {
|
||||
query = SqlUtil.buildCollectionQuery(ID, idsToUpdate);
|
||||
ContentValues values = new ContentValues();
|
||||
values.put(GROUPS_IN_COMMON, 1);
|
||||
int count = db.update(TABLE_NAME, values, query.getWhere(), query.getWhereArgs());
|
||||
if (count > 0) {
|
||||
for (long id : idsToUpdate) {
|
||||
Recipient.live(RecipientId.from(id)).refresh();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void manuallyShowAvatar(@NonNull RecipientId recipientId) {
|
||||
updateExtras(recipientId, b -> b.setManuallyShownAvatar(true));
|
||||
}
|
||||
|
||||
private void updateExtras(@NonNull RecipientId recipientId, @NonNull Function<RecipientExtras.Builder, RecipientExtras.Builder> updater) {
|
||||
SQLiteDatabase db = databaseHelper.getWritableDatabase();
|
||||
db.beginTransaction();
|
||||
try {
|
||||
try (Cursor cursor = db.query(TABLE_NAME, new String[]{ID, EXTRAS}, ID_WHERE, SqlUtil.buildArgs(recipientId), null, null, null)) {
|
||||
if (cursor.moveToNext()) {
|
||||
RecipientExtras state = getRecipientExtras(cursor);
|
||||
RecipientExtras.Builder builder = state != null ? state.toBuilder() : RecipientExtras.newBuilder();
|
||||
byte[] updatedState = updater.apply(builder).build().toByteArray();
|
||||
ContentValues values = new ContentValues(1);
|
||||
values.put(EXTRAS, updatedState);
|
||||
db.update(TABLE_NAME, values, ID_WHERE, SqlUtil.buildArgs(CursorUtil.requireLong(cursor, ID)));
|
||||
}
|
||||
}
|
||||
db.setTransactionSuccessful();
|
||||
} finally {
|
||||
db.endTransaction();
|
||||
}
|
||||
|
||||
Recipient.live(recipientId).refresh();
|
||||
}
|
||||
|
||||
void markDirty(@NonNull RecipientId recipientId, @NonNull DirtyState dirtyState) {
|
||||
Log.d(TAG, "Attempting to mark " + recipientId + " with dirty state " + dirtyState);
|
||||
|
||||
@@ -3232,7 +3352,9 @@ public class RecipientDatabase extends Database {
|
||||
private final ChatWallpaper wallpaper;
|
||||
private final String about;
|
||||
private final String aboutEmoji;
|
||||
private final SyncExtras syncExtras;
|
||||
private final SyncExtras syncExtras;
|
||||
private final Recipient.Extras extras;
|
||||
private final boolean hasGroupsInCommon;
|
||||
|
||||
RecipientSettings(@NonNull RecipientId id,
|
||||
@Nullable UUID uuid,
|
||||
@@ -3273,7 +3395,9 @@ public class RecipientDatabase extends Database {
|
||||
@Nullable ChatWallpaper wallpaper,
|
||||
@Nullable String about,
|
||||
@Nullable String aboutEmoji,
|
||||
@NonNull SyncExtras syncExtras)
|
||||
@NonNull SyncExtras syncExtras,
|
||||
@Nullable Recipient.Extras extras,
|
||||
boolean hasGroupsInCommon)
|
||||
{
|
||||
this.id = id;
|
||||
this.uuid = uuid;
|
||||
@@ -3316,7 +3440,9 @@ public class RecipientDatabase extends Database {
|
||||
this.wallpaper = wallpaper;
|
||||
this.about = about;
|
||||
this.aboutEmoji = aboutEmoji;
|
||||
this.syncExtras = syncExtras;
|
||||
this.syncExtras = syncExtras;
|
||||
this.extras = extras;
|
||||
this.hasGroupsInCommon = hasGroupsInCommon;
|
||||
}
|
||||
|
||||
public RecipientId getId() {
|
||||
@@ -3483,6 +3609,14 @@ public class RecipientDatabase extends Database {
|
||||
return syncExtras;
|
||||
}
|
||||
|
||||
public @Nullable Recipient.Extras getExtras() {
|
||||
return extras;
|
||||
}
|
||||
|
||||
public boolean hasGroupsInCommon() {
|
||||
return hasGroupsInCommon;
|
||||
}
|
||||
|
||||
long getCapabilities() {
|
||||
return capabilities;
|
||||
}
|
||||
|
||||
@@ -43,8 +43,8 @@ import org.thoughtcrime.securesms.database.SignedPreKeyDatabase;
|
||||
import org.thoughtcrime.securesms.database.SmsDatabase;
|
||||
import org.thoughtcrime.securesms.database.SqlCipherDatabaseHook;
|
||||
import org.thoughtcrime.securesms.database.StickerDatabase;
|
||||
import org.thoughtcrime.securesms.database.UnknownStorageIdDatabase;
|
||||
import org.thoughtcrime.securesms.database.ThreadDatabase;
|
||||
import org.thoughtcrime.securesms.database.UnknownStorageIdDatabase;
|
||||
import org.thoughtcrime.securesms.dependencies.ApplicationDependencies;
|
||||
import org.thoughtcrime.securesms.groups.GroupId;
|
||||
import org.thoughtcrime.securesms.jobs.RefreshPreKeysJob;
|
||||
@@ -172,8 +172,9 @@ public class SQLCipherOpenHelper extends SQLiteOpenHelper implements SignalDatab
|
||||
private static final int PAYMENTS = 91;
|
||||
private static final int CLEAN_STORAGE_IDS = 92;
|
||||
private static final int MP4_GIF_SUPPORT = 93;
|
||||
private static final int BLUR_AVATARS = 94;
|
||||
|
||||
private static final int DATABASE_VERSION = 93;
|
||||
private static final int DATABASE_VERSION = 94;
|
||||
private static final String DATABASE_NAME = "signal.db";
|
||||
|
||||
private final Context context;
|
||||
@@ -1304,6 +1305,23 @@ public class SQLCipherOpenHelper extends SQLiteOpenHelper implements SignalDatab
|
||||
db.execSQL("ALTER TABLE part ADD COLUMN video_gif INTEGER DEFAULT 0");
|
||||
}
|
||||
|
||||
if (oldVersion < BLUR_AVATARS) {
|
||||
db.execSQL("ALTER TABLE recipient ADD COLUMN extras BLOB DEFAULT NULL");
|
||||
db.execSQL("ALTER TABLE recipient ADD COLUMN groups_in_common INTEGER DEFAULT 0");
|
||||
|
||||
String secureOutgoingSms = "EXISTS(SELECT 1 FROM sms WHERE thread_id = t._id AND (type & 31) = 23 AND (type & 10485760) AND (type & 131072 = 0))";
|
||||
String secureOutgoingMms = "EXISTS(SELECT 1 FROM mms WHERE thread_id = t._id AND (msg_box & 31) = 23 AND (msg_box & 10485760) AND (msg_box & 131072 = 0))";
|
||||
|
||||
String selectIdsToUpdateProfileSharing = "SELECT r._id FROM recipient AS r INNER JOIN thread AS t ON r._id = t.recipient_ids WHERE profile_sharing = 0 AND (" + secureOutgoingSms + " OR " + secureOutgoingMms + ")";
|
||||
|
||||
db.rawExecSQL("UPDATE recipient SET profile_sharing = 1 WHERE _id IN (" + selectIdsToUpdateProfileSharing + ")");
|
||||
|
||||
String selectIdsWithGroupsInCommon = "SELECT r._id FROM recipient AS r WHERE EXISTS("
|
||||
+ "SELECT 1 FROM groups AS g INNER JOIN recipient AS gr ON (g.recipient_id = gr._id AND gr.profile_sharing = 1) WHERE g.active = 1 AND (g.members LIKE r._id || ',%' OR g.members LIKE '%,' || r._id || ',%' OR g.members LIKE '%,' || r._id)"
|
||||
+ ")";
|
||||
db.rawExecSQL("UPDATE recipient SET groups_in_common = 1 WHERE _id IN (" + selectIdsWithGroupsInCommon + ")");
|
||||
}
|
||||
|
||||
db.setTransactionSuccessful();
|
||||
} finally {
|
||||
db.endTransaction();
|
||||
|
||||
Reference in New Issue
Block a user