cache some information generated from body like isEmojiOnly, fileParams and isGeoUri

This commit is contained in:
Daniel Gultsch 2017-08-03 13:24:41 +02:00
parent 7bcf173866
commit c3cbb21133
6 changed files with 98 additions and 118 deletions

View file

@ -90,6 +90,11 @@ public class Message extends AbstractEntity {
private String axolotlFingerprint = null;
private String errorMessage = null;
private Boolean isGeoUri = null;
private Boolean isEmojisOnly = null;
private Boolean treatAsDownloadable = null;
private FileParams fileParams = null;
private Message(Conversation conversation) {
this.conversation = conversation;
}
@ -195,21 +200,21 @@ public class Message extends AbstractEntity {
public static Message createStatusMessage(Conversation conversation, String body) {
final Message message = new Message(conversation);
message.setType(Message.TYPE_STATUS);
message.setBody(body);
message.body = body;
return message;
}
public static Message createLoadMoreMessage(Conversation conversation) {
final Message message = new Message(conversation);
message.setType(Message.TYPE_STATUS);
message.setBody("LOAD_MORE");
message.body = "LOAD_MORE";
return message;
}
public static Message createDateSeparator(Message message) {
final Message separator = new Message(message.getConversation());
separator.setType(Message.TYPE_STATUS);
separator.setBody(MessageAdapter.DATE_SEPARATOR_BODY);
separator.body = MessageAdapter.DATE_SEPARATOR_BODY;
separator.setTime(message.getTimeSent());
return separator;
}
@ -279,11 +284,15 @@ public class Message extends AbstractEntity {
return body;
}
public void setBody(String body) {
public synchronized void setBody(String body) {
if (body == null) {
throw new Error("You should not set the message body to null");
}
this.body = body;
this.isGeoUri = null;
this.isEmojisOnly = null;
this.treatAsDownloadable = null;
this.fileParams = null;
}
public String getErrorMessage() {
@ -401,7 +410,8 @@ public class Message extends AbstractEntity {
return this.transferable;
}
public void setTransferable(Transferable transferable) {
public synchronized void setTransferable(Transferable transferable) {
this.fileParams = null;
this.transferable = transferable;
}
@ -496,8 +506,8 @@ public class Message extends AbstractEntity {
this.edited() == message.edited() &&
(message.getTimeSent() - this.getTimeSent()) <= (Config.MESSAGE_MERGE_WINDOW * 1000) &&
this.getBody().length() + message.getBody().length() <= Config.MAX_DISPLAY_MESSAGE_CHARS &&
!GeoHelper.isGeoUri(message.getBody()) &&
!GeoHelper.isGeoUri(this.body) &&
!message.isGeoUri()&&
!this.isGeoUri() &&
!message.treatAsDownloadable() &&
!this.treatAsDownloadable() &&
!message.getBody().startsWith(ME_COMMAND) &&
@ -651,120 +661,92 @@ public class Message extends AbstractEntity {
}
}
public boolean treatAsDownloadable() {
public synchronized boolean treatAsDownloadable() {
if (treatAsDownloadable == null) {
if (body.trim().contains(" ")) {
return false;
treatAsDownloadable = false;
}
try {
final URL url = new URL(body);
final String ref = url.getRef();
final String protocol = url.getProtocol();
final boolean encrypted = ref != null && ref.matches("([A-Fa-f0-9]{2}){48}");
return (AesGcmURLStreamHandler.PROTOCOL_NAME.equalsIgnoreCase(protocol) && encrypted)
treatAsDownloadable = (AesGcmURLStreamHandler.PROTOCOL_NAME.equalsIgnoreCase(protocol) && encrypted)
|| (("http".equalsIgnoreCase(protocol) || "https".equalsIgnoreCase(protocol)) && (oob || encrypted));
} catch (MalformedURLException e) {
return false;
treatAsDownloadable = false;
}
}
return treatAsDownloadable;
}
public boolean bodyIsOnlyEmojis() {
return EmojiManager.isOnlyEmojis(body.replaceAll("\\s",""));
public synchronized boolean bodyIsOnlyEmojis() {
if (isEmojisOnly == null) {
isEmojisOnly = EmojiManager.isOnlyEmojis(body.replaceAll("\\s", ""));
}
return isEmojisOnly;
}
public FileParams getFileParams() {
FileParams params = getLegacyFileParams();
if (params != null) {
return params;
public synchronized boolean isGeoUri() {
if (isGeoUri == null) {
isGeoUri = GeoHelper.GEO_URI.matcher(body).matches();
}
params = new FileParams();
return isGeoUri;
}
public synchronized FileParams getFileParams() {
if (fileParams == null) {
fileParams = new FileParams();
if (this.transferable != null) {
params.size = this.transferable.getFileSize();
fileParams.size = this.transferable.getFileSize();
}
if (body == null) {
return params;
}
String parts[] = body.split("\\|");
String parts[] = body == null ? new String[0] : body.split("\\|");
switch (parts.length) {
case 1:
try {
params.size = Long.parseLong(parts[0]);
fileParams.size = Long.parseLong(parts[0]);
} catch (NumberFormatException e) {
try {
params.url = new URL(parts[0]);
} catch (MalformedURLException e1) {
params.url = null;
}
fileParams.url = parseUrl(parts[0]);
}
break;
case 2:
case 4:
try {
params.url = new URL(parts[0]);
} catch (MalformedURLException e1) {
params.url = null;
}
try {
params.size = Long.parseLong(parts[1]);
} catch (NumberFormatException e) {
params.size = 0;
}
try {
params.width = Integer.parseInt(parts[2]);
} catch (NumberFormatException | ArrayIndexOutOfBoundsException e) {
params.width = 0;
}
try {
params.height = Integer.parseInt(parts[3]);
} catch (NumberFormatException | ArrayIndexOutOfBoundsException e) {
params.height = 0;
}
fileParams.width = parseInt(parts[2]);
fileParams.height = parseInt(parts[3]);
case 2:
fileParams.url = parseUrl(parts[0]);
fileParams.size = parseLong(parts[1]);
break;
case 3:
try {
params.size = Long.parseLong(parts[0]);
} catch (NumberFormatException e) {
params.size = 0;
}
try {
params.width = Integer.parseInt(parts[1]);
} catch (NumberFormatException e) {
params.width = 0;
}
try {
params.height = Integer.parseInt(parts[2]);
} catch (NumberFormatException e) {
params.height = 0;
}
fileParams.size = parseLong(parts[0]);
fileParams.width = parseInt(parts[1]);
fileParams.height = parseInt(parts[2]);
break;
}
return params;
}
return fileParams;
}
public FileParams getLegacyFileParams() {
FileParams params = new FileParams();
if (body == null) {
return params;
}
String parts[] = body.split(",");
if (parts.length == 3) {
private static long parseLong(String value) {
try {
params.size = Long.parseLong(parts[0]);
return Long.parseLong(value);
} catch (NumberFormatException e) {
return null;
return 0;
}
}
private static int parseInt(String value) {
try {
params.width = Integer.parseInt(parts[1]);
return Integer.parseInt(value);
} catch (NumberFormatException e) {
return null;
return 0;
}
}
private static URL parseUrl(String value) {
try {
params.height = Integer.parseInt(parts[2]);
} catch (NumberFormatException e) {
return null;
}
return params;
} else {
return new URL(value);
} catch (MalformedURLException e) {
return null;
}
}

View file

@ -531,7 +531,7 @@ public class NotificationService {
private Message getFirstLocationMessage(final Iterable<Message> messages) {
for (final Message message : messages) {
if (GeoHelper.isGeoUri(message.getBody())) {
if (message.isGeoUri()) {
return message;
}
}

View file

@ -618,7 +618,7 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa
MenuItem cancelTransmission = menu.findItem(R.id.cancel_transmission);
MenuItem deleteFile = menu.findItem(R.id.delete_file);
MenuItem showErrorMessage = menu.findItem(R.id.show_error_message);
if (!treatAsFile && !GeoHelper.isGeoUri(m.getBody()) && !m.treatAsDownloadable()) {
if (!treatAsFile && !m.isGeoUri() && !m.treatAsDownloadable()) {
selectText.setVisible(ListSelectionManager.isSupported());
}
if (m.getEncryption() == Message.ENCRYPTION_DECRYPTION_FAILED) {
@ -636,7 +636,7 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa
sendAgain.setVisible(true);
}
if (m.hasFileOnRemoteHost()
|| GeoHelper.isGeoUri(m.getBody())
|| m.isGeoUri()
|| m.treatAsDownloadable()
|| (t != null && t instanceof HttpDownloadConnection)) {
copyUrl.setVisible(true);
@ -713,7 +713,7 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa
private void shareWith(Message message) {
Intent shareIntent = new Intent();
shareIntent.setAction(Intent.ACTION_SEND);
if (GeoHelper.isGeoUri(message.getBody())) {
if (message.isGeoUri()) {
shareIntent.putExtra(Intent.EXTRA_TEXT, message.getBody());
shareIntent.setType("text/plain");
} else if (!message.isFileOrImage()) {
@ -785,7 +785,7 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa
private void copyUrl(Message message) {
final String url;
final int resId;
if (GeoHelper.isGeoUri(message.getBody())) {
if (message.isGeoUri()) {
resId = R.string.location;
url = message.getBody();
} else if (message.hasFileOnRemoteHost()) {

View file

@ -790,7 +790,7 @@ public class MessageAdapter extends ArrayAdapter<Message> implements CopyTextVie
} else if (message.getEncryption() == Message.ENCRYPTION_DECRYPTION_FAILED) {
displayDecryptionFailed(viewHolder,darkBackground);
} else {
if (GeoHelper.isGeoUri(message.getBody())) {
if (message.isGeoUri()) {
displayLocationMessage(viewHolder,message);
} else if (message.bodyIsOnlyEmojis()) {
displayEmojiMessage(viewHolder, message.getBody().replaceAll("\\s",""));

View file

@ -16,9 +16,7 @@ import eu.siacs.conversations.entities.Message;
public class GeoHelper {
public static Pattern GEO_URI = Pattern.compile("geo:([\\-0-9.]+),([\\-0-9.]+)(?:,([\\-0-9.]+))?(?:\\?(.*))?", Pattern.CASE_INSENSITIVE);
public static boolean isGeoUri(String body) {
return body != null && GEO_URI.matcher(body).matches();
}
public static ArrayList<Intent> createGeoIntentsFromMessage(Message message) {
final ArrayList<Intent> intents = new ArrayList<>();

View file

@ -202,7 +202,7 @@ public class UIHelper {
if (body.startsWith(Message.ME_COMMAND)) {
return new Pair<>(body.replaceAll("^" + Message.ME_COMMAND,
UIHelper.getMessageDisplayName(message) + " "), false);
} else if (GeoHelper.isGeoUri(message.getBody())) {
} else if (message.isGeoUri()) {
if (message.getStatus() == Message.STATUS_RECEIVED) {
return new Pair<>(context.getString(R.string.received_location), true);
} else {