kopia lustrzana https://github.com/ryukoposting/Signal-Android
Turned SingleUseBlobProvider into MemoryBlobProvider.
Keep the single-use behavior, but allow the creation of multi-use memory blobs that can be deleted when we're done with them. Will help out with having URI's for temporary images during the camera capture flow.fork-5.53.8
rodzic
e63773e5c8
commit
e9a38bab1e
|
@ -16,7 +16,7 @@ import org.thoughtcrime.securesms.database.DatabaseFactory;
|
|||
import org.thoughtcrime.securesms.database.GroupDatabase;
|
||||
import org.thoughtcrime.securesms.database.ThreadDatabase;
|
||||
import org.thoughtcrime.securesms.mms.OutgoingGroupMediaMessage;
|
||||
import org.thoughtcrime.securesms.providers.SingleUseBlobProvider;
|
||||
import org.thoughtcrime.securesms.providers.MemoryBlobProvider;
|
||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||
import org.thoughtcrime.securesms.sms.MessageSender;
|
||||
import org.thoughtcrime.securesms.util.BitmapUtil;
|
||||
|
@ -111,7 +111,7 @@ public class GroupManager {
|
|||
GroupContext groupContext = groupContextBuilder.build();
|
||||
|
||||
if (avatar != null) {
|
||||
Uri avatarUri = SingleUseBlobProvider.getInstance().createUri(avatar);
|
||||
Uri avatarUri = MemoryBlobProvider.getInstance().createSingleUseUri(avatar);
|
||||
avatarAttachment = new UriAttachment(avatarUri, MediaUtil.IMAGE_PNG, AttachmentDatabase.TRANSFER_PROGRESS_DONE, avatar.length, null, false, false);
|
||||
}
|
||||
|
||||
|
|
|
@ -29,7 +29,7 @@ import org.thoughtcrime.securesms.mms.MmsException;
|
|||
import org.thoughtcrime.securesms.mms.MmsRadioException;
|
||||
import org.thoughtcrime.securesms.mms.PartParser;
|
||||
import org.thoughtcrime.securesms.notifications.MessageNotifier;
|
||||
import org.thoughtcrime.securesms.providers.SingleUseBlobProvider;
|
||||
import org.thoughtcrime.securesms.providers.MemoryBlobProvider;
|
||||
import org.thoughtcrime.securesms.service.KeyCachingService;
|
||||
import org.thoughtcrime.securesms.util.TextSecurePreferences;
|
||||
import org.thoughtcrime.securesms.util.Util;
|
||||
|
@ -174,7 +174,7 @@ public class MmsDownloadJob extends MasterSecretJob {
|
|||
LegacyMessageException
|
||||
{
|
||||
MmsDatabase database = DatabaseFactory.getMmsDatabase(context);
|
||||
SingleUseBlobProvider provider = SingleUseBlobProvider.getInstance();
|
||||
MemoryBlobProvider provider = MemoryBlobProvider.getInstance();
|
||||
Optional<Address> group = Optional.absent();
|
||||
Set<Address> members = new HashSet<>();
|
||||
String body = null;
|
||||
|
@ -213,7 +213,7 @@ public class MmsDownloadJob extends MasterSecretJob {
|
|||
PduPart part = media.getPart(i);
|
||||
|
||||
if (part.getData() != null) {
|
||||
Uri uri = provider.createUri(part.getData());
|
||||
Uri uri = provider.createSingleUseUri(part.getData());
|
||||
String name = null;
|
||||
|
||||
if (part.getName() != null) name = Util.toIsoString(part.getName());
|
||||
|
|
|
@ -9,11 +9,10 @@ import android.support.annotation.Nullable;
|
|||
|
||||
import org.thoughtcrime.securesms.attachments.Attachment;
|
||||
import org.thoughtcrime.securesms.attachments.AttachmentId;
|
||||
import org.thoughtcrime.securesms.crypto.MasterSecret;
|
||||
import org.thoughtcrime.securesms.database.DatabaseFactory;
|
||||
import org.thoughtcrime.securesms.providers.PersistentBlobProvider;
|
||||
import org.thoughtcrime.securesms.providers.PartProvider;
|
||||
import org.thoughtcrime.securesms.providers.SingleUseBlobProvider;
|
||||
import org.thoughtcrime.securesms.providers.MemoryBlobProvider;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
|
@ -38,7 +37,7 @@ public class PartAuthority {
|
|||
uriMatcher.addURI("org.thoughtcrime.securesms", "thumb/*/#", THUMB_ROW);
|
||||
uriMatcher.addURI(PersistentBlobProvider.AUTHORITY, PersistentBlobProvider.EXPECTED_PATH_OLD, PERSISTENT_ROW);
|
||||
uriMatcher.addURI(PersistentBlobProvider.AUTHORITY, PersistentBlobProvider.EXPECTED_PATH_NEW, PERSISTENT_ROW);
|
||||
uriMatcher.addURI(SingleUseBlobProvider.AUTHORITY, SingleUseBlobProvider.PATH, SINGLE_USE_ROW);
|
||||
uriMatcher.addURI(MemoryBlobProvider.AUTHORITY, MemoryBlobProvider.PATH, SINGLE_USE_ROW);
|
||||
}
|
||||
|
||||
public static InputStream getAttachmentStream(@NonNull Context context, @NonNull Uri uri)
|
||||
|
@ -50,7 +49,7 @@ public class PartAuthority {
|
|||
case PART_ROW: return DatabaseFactory.getAttachmentDatabase(context).getAttachmentStream(new PartUriParser(uri).getPartId(), 0);
|
||||
case THUMB_ROW: return DatabaseFactory.getAttachmentDatabase(context).getThumbnailStream(new PartUriParser(uri).getPartId());
|
||||
case PERSISTENT_ROW: return PersistentBlobProvider.getInstance(context).getStream(context, ContentUris.parseId(uri));
|
||||
case SINGLE_USE_ROW: return SingleUseBlobProvider.getInstance().getStream(ContentUris.parseId(uri));
|
||||
case SINGLE_USE_ROW: return MemoryBlobProvider.getInstance().getStream(ContentUris.parseId(uri));
|
||||
default: return context.getContentResolver().openInputStream(uri);
|
||||
}
|
||||
} catch (SecurityException se) {
|
||||
|
|
|
@ -0,0 +1,90 @@
|
|||
package org.thoughtcrime.securesms.providers;
|
||||
|
||||
import android.content.ContentUris;
|
||||
import android.net.Uri;
|
||||
import android.support.annotation.NonNull;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.security.SecureRandom;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
public class MemoryBlobProvider {
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private static final String TAG = MemoryBlobProvider.class.getSimpleName();
|
||||
|
||||
public static final String AUTHORITY = "org.thoughtcrime.securesms";
|
||||
public static final String PATH = "memory/*/#";
|
||||
private static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITY + "/memory");
|
||||
|
||||
private final Map<Long, Entry> cache = new HashMap<>();
|
||||
|
||||
private static final MemoryBlobProvider instance = new MemoryBlobProvider();
|
||||
|
||||
public static MemoryBlobProvider getInstance() {
|
||||
return instance;
|
||||
}
|
||||
|
||||
private MemoryBlobProvider() {}
|
||||
|
||||
public synchronized Uri createSingleUseUri(@NonNull byte[] blob) {
|
||||
return createUriInternal(blob, true);
|
||||
}
|
||||
|
||||
public synchronized Uri createUri(@NonNull byte[] blob) {
|
||||
return createUriInternal(blob, false);
|
||||
}
|
||||
|
||||
public synchronized void delete(@NonNull Uri uri) {
|
||||
cache.remove(ContentUris.parseId(uri));
|
||||
}
|
||||
|
||||
public synchronized @NonNull InputStream getStream(long id) throws IOException {
|
||||
Entry entry = cache.get(id);
|
||||
|
||||
if (entry == null) {
|
||||
throw new IOException("ID not found: " + id);
|
||||
}
|
||||
|
||||
if (entry.isSingleUse()) {
|
||||
cache.remove(id);
|
||||
}
|
||||
|
||||
return new ByteArrayInputStream(entry.getBlob());
|
||||
}
|
||||
|
||||
private Uri createUriInternal(@NonNull byte[] blob, boolean singleUse) {
|
||||
try {
|
||||
long id = Math.abs(SecureRandom.getInstance("SHA1PRNG").nextLong());
|
||||
cache.put(id, new Entry(blob, singleUse));
|
||||
|
||||
Uri uniqueUri = Uri.withAppendedPath(CONTENT_URI, String.valueOf(System.currentTimeMillis()));
|
||||
return ContentUris.withAppendedId(uniqueUri, id);
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
throw new AssertionError(e);
|
||||
}
|
||||
}
|
||||
|
||||
private static class Entry {
|
||||
|
||||
private final byte[] blob;
|
||||
private final boolean singleUse;
|
||||
|
||||
private Entry(@NonNull byte[] blob, boolean singleUse) {
|
||||
this.blob = blob;
|
||||
this.singleUse = singleUse;
|
||||
}
|
||||
|
||||
public byte[] getBlob() {
|
||||
return blob;
|
||||
}
|
||||
|
||||
public boolean isSingleUse() {
|
||||
return singleUse;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,55 +0,0 @@
|
|||
package org.thoughtcrime.securesms.providers;
|
||||
|
||||
import android.content.ContentUris;
|
||||
import android.net.Uri;
|
||||
import android.support.annotation.NonNull;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.security.SecureRandom;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
public class SingleUseBlobProvider {
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private static final String TAG = SingleUseBlobProvider.class.getSimpleName();
|
||||
|
||||
public static final String AUTHORITY = "org.thoughtcrime.securesms";
|
||||
public static final String PATH = "memory/*/#";
|
||||
private static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITY + "/memory");
|
||||
|
||||
private final Map<Long, byte[]> cache = new HashMap<>();
|
||||
|
||||
private static final SingleUseBlobProvider instance = new SingleUseBlobProvider();
|
||||
|
||||
public static SingleUseBlobProvider getInstance() {
|
||||
return instance;
|
||||
}
|
||||
|
||||
private SingleUseBlobProvider() {}
|
||||
|
||||
public synchronized Uri createUri(@NonNull byte[] blob) {
|
||||
try {
|
||||
long id = Math.abs(SecureRandom.getInstance("SHA1PRNG").nextLong());
|
||||
cache.put(id, blob);
|
||||
|
||||
Uri uniqueUri = Uri.withAppendedPath(CONTENT_URI, String.valueOf(System.currentTimeMillis()));
|
||||
return ContentUris.withAppendedId(uniqueUri, id);
|
||||
} catch (NoSuchAlgorithmException e) {
|
||||
throw new AssertionError(e);
|
||||
}
|
||||
}
|
||||
|
||||
public synchronized @NonNull InputStream getStream(long id) throws IOException {
|
||||
byte[] cached = cache.get(id);
|
||||
cache.remove(id);
|
||||
|
||||
if (cached != null) return new ByteArrayInputStream(cached);
|
||||
else throw new IOException("ID not found: " + id);
|
||||
|
||||
}
|
||||
|
||||
}
|
Ładowanie…
Reference in New Issue