X-Git-Url: https://git.nmode.ca/signal-cli/blobdiff_plain/ff998fce578ebc035439f8eaad8e1b48e482a3c5..9e6a3534275d5bac8454792e05280f13fa5ef13c:/src/main/java/org/asamk/signal/manager/Manager.java diff --git a/src/main/java/org/asamk/signal/manager/Manager.java b/src/main/java/org/asamk/signal/manager/Manager.java index e02106b9..c958e0a4 100644 --- a/src/main/java/org/asamk/signal/manager/Manager.java +++ b/src/main/java/org/asamk/signal/manager/Manager.java @@ -18,6 +18,13 @@ package org.asamk.signal.manager; import com.fasterxml.jackson.databind.ObjectMapper; +import org.asamk.signal.manager.groups.GroupId; +import org.asamk.signal.manager.groups.GroupIdV1; +import org.asamk.signal.manager.groups.GroupIdV2; +import org.asamk.signal.manager.groups.GroupInviteLinkUrl; +import org.asamk.signal.manager.groups.GroupNotFoundException; +import org.asamk.signal.manager.groups.GroupUtils; +import org.asamk.signal.manager.groups.NotAGroupMemberException; import org.asamk.signal.manager.helper.GroupHelper; import org.asamk.signal.manager.helper.ProfileHelper; import org.asamk.signal.manager.helper.UnidentifiedAccessHelper; @@ -55,6 +62,8 @@ import org.signal.zkgroup.groups.GroupSecretParams; import org.signal.zkgroup.profiles.ClientZkProfileOperations; import org.signal.zkgroup.profiles.ProfileKey; import org.signal.zkgroup.profiles.ProfileKeyCredential; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import org.whispersystems.libsignal.IdentityKey; import org.whispersystems.libsignal.IdentityKeyPair; import org.whispersystems.libsignal.InvalidKeyException; @@ -173,6 +182,8 @@ import static org.asamk.signal.manager.ServiceConfig.getIasKeyStore; public class Manager implements Closeable { + final static Logger logger = LoggerFactory.getLogger(Manager.class); + private final SleepTimer timer = new UptimeSleepTimer(); private final SignalServiceConfiguration serviceConfiguration; @@ -255,26 +266,26 @@ public class Manager implements Closeable { return account.getDeviceId(); } - private String getMessageCachePath() { - return pathConfig.getDataPath() + "/" + account.getUsername() + ".d/msg-cache"; + private File getMessageCachePath() { + return SignalAccount.getMessageCachePath(pathConfig.getDataPath(), account.getUsername()); } - private String getMessageCachePath(String sender) { + private File getMessageCachePath(String sender) { if (sender == null || sender.isEmpty()) { return getMessageCachePath(); } - return getMessageCachePath() + "/" + sender.replace("/", "_"); + return new File(getMessageCachePath(), sender.replace("/", "_")); } private File getMessageCacheFile(String sender, long now, long timestamp) throws IOException { - String cachePath = getMessageCachePath(sender); + File cachePath = getMessageCachePath(sender); IOUtils.createPrivateDirectories(cachePath); - return new File(cachePath + "/" + now + "_" + timestamp); + return new File(cachePath, now + "_" + timestamp); } public static Manager init( - String username, String settingsPath, SignalServiceConfiguration serviceConfiguration, String userAgent + String username, File settingsPath, SignalServiceConfiguration serviceConfiguration, String userAgent ) throws IOException { PathConfig pathConfig = PathConfig.createDefault(settingsPath); @@ -590,7 +601,7 @@ public class Manager implements Closeable { try { profile = retrieveRecipientProfile(address, profileKey); } catch (IOException e) { - System.err.println("Failed to retrieve profile, ignoring: " + e.getMessage()); + logger.warn("Failed to retrieve profile, ignoring: {}", e.getMessage()); profileEntry.setRequestPending(false); return null; } @@ -613,7 +624,7 @@ public class Manager implements Closeable { profileAndCredential = profileHelper.retrieveProfileSync(address, SignalServiceProfile.RequestType.PROFILE_AND_CREDENTIAL); } catch (IOException e) { - System.err.println("Failed to retrieve profile key credential, ignoring: " + e.getMessage()); + logger.warn("Failed to retrieve profile key credential, ignoring: {}", e.getMessage()); return null; } @@ -646,7 +657,7 @@ public class Manager implements Closeable { ? null : retrieveProfileAvatar(address, encryptedProfile.getAvatar(), profileKey); } catch (Throwable e) { - System.err.println("Failed to retrieve profile avatar, ignoring: " + e.getMessage()); + logger.warn("Failed to retrieve profile avatar, ignoring: {}", e.getMessage()); } ProfileCipher profileCipher = new ProfileCipher(profileKey); @@ -816,7 +827,10 @@ public class Manager implements Closeable { if (members != null) { final Set newMembers = new HashSet<>(members); - newMembers.removeAll(group.getMembers()); + newMembers.removeAll(group.getMembers() + .stream() + .map(this::resolveSignalServiceAddress) + .collect(Collectors.toSet())); if (newMembers.size() > 0) { Pair groupGroupChangePair = groupHelper.updateGroupV2(groupInfoV2, newMembers); @@ -1154,7 +1168,7 @@ public class Manager implements Closeable { * @param path Path can be a path to a manifest.json file or to a zip file that contains a manifest.json file * @return if successful, returns the URL to install the sticker pack in the signal app */ - public String uploadStickerPack(String path) throws IOException, StickerPackInvalidException { + public String uploadStickerPack(File path) throws IOException, StickerPackInvalidException { SignalServiceStickerManifestUpload manifest = getSignalServiceStickerManifestUpload(path); SignalServiceMessageSender messageSender = createMessageSender(); @@ -1179,12 +1193,11 @@ public class Manager implements Closeable { } private SignalServiceStickerManifestUpload getSignalServiceStickerManifestUpload( - final String path + final File file ) throws IOException, StickerPackInvalidException { ZipFile zip = null; String rootPath = null; - final File file = new File(path); if (file.getName().endsWith(".zip")) { zip = new ZipFile(file); } else if (file.getName().equals("manifest.json")) { @@ -1324,7 +1337,7 @@ public class Manager implements Closeable { try { certificate = accountManager.getSenderCertificate(); } catch (IOException e) { - System.err.println("Failed to get sender certificate: " + e); + logger.warn("Failed to get sender certificate, ignoring: {}", e.getMessage()); return null; } // TODO cache for a day @@ -1363,7 +1376,7 @@ public class Manager implements Closeable { missingUuids.stream().map(a -> a.getNumber().get()).collect(Collectors.toSet()), CDS_MRENCLAVE); } catch (IOException | Quote.InvalidQuoteFormatException | UnauthenticatedQuoteException | SignatureException | UnauthenticatedResponseException e) { - System.err.println("Failed to resolve uuids from server: " + e.getMessage()); + logger.warn("Failed to resolve uuids from server, ignoring: {}", e.getMessage()); registeredUsers = new HashMap<>(); } @@ -1567,8 +1580,9 @@ public class Manager implements Closeable { try { retrieveGroupAvatarAttachment(avatar.asPointer(), groupV1.getGroupId()); } catch (IOException | InvalidMessageException | MissingConfigurationException e) { - System.err.println("Failed to retrieve group avatar (" + avatar.asPointer() - .getRemoteId() + "): " + e.getMessage()); + logger.warn("Failed to retrieve avatar for group {}, ignoring: {}", + groupId.toBase64(), + e.getMessage()); } } } @@ -1590,7 +1604,7 @@ public class Manager implements Closeable { } case DELIVER: if (groupV1 == null && !isSync) { - actions.add(new SendGroupInfoRequestAction(source, groupV1.getGroupId())); + actions.add(new SendGroupInfoRequestAction(source, groupId)); } break; case QUIT: { @@ -1655,10 +1669,9 @@ public class Manager implements Closeable { try { retrieveAttachment(attachment.asPointer()); } catch (IOException | InvalidMessageException | MissingConfigurationException e) { - System.err.println("Failed to retrieve attachment (" - + attachment.asPointer().getRemoteId() - + "): " - + e.getMessage()); + logger.warn("Failed to retrieve attachment ({}), ignoring: {}", + attachment.asPointer().getRemoteId(), + e.getMessage()); } } } @@ -1683,10 +1696,9 @@ public class Manager implements Closeable { try { retrieveAttachment(attachment); } catch (IOException | InvalidMessageException | MissingConfigurationException e) { - System.err.println("Failed to retrieve attachment (" - + attachment.getRemoteId() - + "): " - + e.getMessage()); + logger.warn("Failed to retrieve preview image ({}), ignoring: {}", + attachment.getRemoteId(), + e.getMessage()); } } } @@ -1700,10 +1712,9 @@ public class Manager implements Closeable { try { retrieveAttachment(attachment.asPointer()); } catch (IOException | InvalidMessageException | MissingConfigurationException e) { - System.err.println("Failed to retrieve attachment (" - + attachment.asPointer().getRemoteId() - + "): " - + e.getMessage()); + logger.warn("Failed to retrieve quote attachment thumbnail ({}), ignoring: {}", + attachment.asPointer().getRemoteId(), + e.getMessage()); } } } @@ -1731,11 +1742,9 @@ public class Manager implements Closeable { // Received a v2 group message for a v1 group, we need to locally migrate the group account.getGroupStore().deleteGroup(groupInfo.getGroupId()); groupInfoV2 = new GroupInfoV2(groupId, groupMasterKey); - System.err.println("Locally migrated group " - + groupInfo.getGroupId().toBase64() - + " to group v2, id: " - + groupInfoV2.getGroupId().toBase64() - + " !!!"); + logger.info("Locally migrated group {} to group v2, id: {}", + groupInfo.getGroupId().toBase64(), + groupInfoV2.getGroupId().toBase64()); } else if (groupInfo instanceof GroupInfoV2) { groupInfoV2 = (GroupInfoV2) groupInfo; } else { @@ -1754,10 +1763,13 @@ public class Manager implements Closeable { } if (group != null) { storeProfileKeysFromMembers(group); - try { - retrieveGroupAvatar(groupId, groupSecretParams, group.getAvatar()); - } catch (IOException e) { - System.err.println("Failed to download group avatar, ignoring ..."); + final String avatar = group.getAvatar(); + if (avatar != null && !avatar.isEmpty()) { + try { + retrieveGroupAvatar(groupId, groupSecretParams, avatar); + } catch (IOException e) { + logger.warn("Failed to download group avatar, ignoring: {}", e.getMessage()); + } } } groupInfoV2.setGroup(group); @@ -1782,7 +1794,7 @@ public class Manager implements Closeable { private void retryFailedReceivedMessages( ReceiveMessageHandler handler, boolean ignoreAttachments ) { - final File cachePath = new File(getMessageCachePath()); + final File cachePath = getMessageCachePath(); if (!cachePath.exists()) { return; } @@ -1827,7 +1839,7 @@ public class Manager implements Closeable { try { Files.delete(fileEntry.toPath()); } catch (IOException e) { - System.err.println("Failed to delete cached message file “" + fileEntry + "”: " + e.getMessage()); + logger.warn("Failed to delete cached message file “{}”, ignoring: {}", fileEntry, e.getMessage()); } return; } @@ -1845,7 +1857,7 @@ public class Manager implements Closeable { try { Files.delete(fileEntry.toPath()); } catch (IOException e) { - System.err.println("Failed to delete cached message file “" + fileEntry + "”: " + e.getMessage()); + logger.warn("Failed to delete cached message file “{}”, ignoring: {}", fileEntry, e.getMessage()); } } @@ -1877,8 +1889,7 @@ public class Manager implements Closeable { File cacheFile = getMessageCacheFile(source, now, envelope1.getTimestamp()); Utils.storeEnvelope(envelope1, cacheFile); } catch (IOException e) { - System.err.println("Failed to store encrypted message in disk cache, ignoring: " - + e.getMessage()); + logger.warn("Failed to store encrypted message in disk cache, ignoring: {}", e.getMessage()); } }); if (result.isPresent()) { @@ -1907,7 +1918,7 @@ public class Manager implements Closeable { if (returnOnTimeout) return; continue; } catch (InvalidVersionException e) { - System.err.println("Ignoring error: " + e.getMessage()); + logger.warn("Error while receiving messages, ignoring: {}", e.getMessage()); continue; } @@ -1949,9 +1960,9 @@ public class Manager implements Closeable { cacheFile = getMessageCacheFile(source, now, envelope.getTimestamp()); Files.delete(cacheFile.toPath()); // Try to delete directory if empty - new File(getMessageCachePath()).delete(); + getMessageCachePath().delete(); } catch (IOException e) { - System.err.println("Failed to delete cached message file “" + cacheFile + "”: " + e.getMessage()); + logger.warn("Failed to delete cached message file “{}”, ignoring: {}", cacheFile, e.getMessage()); } } } @@ -2085,16 +2096,18 @@ public class Manager implements Closeable { } } } catch (Exception e) { + logger.warn("Failed to handle received sync groups “{}”, ignoring: {}", + tmpFile, + e.getMessage()); e.printStackTrace(); } finally { if (tmpFile != null) { try { Files.delete(tmpFile.toPath()); } catch (IOException e) { - System.err.println("Failed to delete received groups temp file “" - + tmpFile - + "”: " - + e.getMessage()); + logger.warn("Failed to delete received groups temp file “{}”, ignoring: {}", + tmpFile, + e.getMessage()); } } } @@ -2111,8 +2124,8 @@ public class Manager implements Closeable { try { setGroupBlocked(groupId, true); } catch (GroupNotFoundException e) { - System.err.println("BlockedListMessage contained groupID that was not found in GroupStore: " - + groupId.toBase64()); + logger.warn("BlockedListMessage contained groupID that was not found in GroupStore: {}", + groupId.toBase64()); } } } @@ -2173,10 +2186,9 @@ public class Manager implements Closeable { try { Files.delete(tmpFile.toPath()); } catch (IOException e) { - System.err.println("Failed to delete received contacts temp file “" - + tmpFile - + "”: " - + e.getMessage()); + logger.warn("Failed to delete received contacts temp file “{}”, ignoring: {}", + tmpFile, + e.getMessage()); } } } @@ -2272,7 +2284,9 @@ public class Manager implements Closeable { try { Files.delete(tmpFile.toPath()); } catch (IOException e) { - System.err.println("Failed to delete received avatar temp file “" + tmpFile + "”: " + e.getMessage()); + logger.warn("Failed to delete received group avatar temp file “{}”, ignoring: {}", + tmpFile, + e.getMessage()); } } return outputFile; @@ -2300,7 +2314,9 @@ public class Manager implements Closeable { try { Files.delete(tmpFile.toPath()); } catch (IOException e) { - System.err.println("Failed to delete received avatar temp file “" + tmpFile + "”: " + e.getMessage()); + logger.warn("Failed to delete received profile avatar temp file “{}”, ignoring: {}", + tmpFile, + e.getMessage()); } } return outputFile; @@ -2340,10 +2356,9 @@ public class Manager implements Closeable { try { Files.delete(tmpFile.toPath()); } catch (IOException e) { - System.err.println("Failed to delete received attachment temp file “" - + tmpFile - + "”: " - + e.getMessage()); + logger.warn("Failed to delete received attachment temp file “{}”, ignoring: {}", + tmpFile, + e.getMessage()); } } return outputFile; @@ -2394,7 +2409,7 @@ public class Manager implements Closeable { try { Files.delete(groupsFile.toPath()); } catch (IOException e) { - System.err.println("Failed to delete groups temp file “" + groupsFile + "”: " + e.getMessage()); + logger.warn("Failed to delete groups temp file “{}”, ignoring: {}", groupsFile, e.getMessage()); } } } @@ -2459,7 +2474,7 @@ public class Manager implements Closeable { try { Files.delete(contactsFile.toPath()); } catch (IOException e) { - System.err.println("Failed to delete contacts temp file “" + contactsFile + "”: " + e.getMessage()); + logger.warn("Failed to delete contacts temp file “{}”, ignoring: {}", contactsFile, e.getMessage()); } } }