mirror of
https://github.com/AsamK/signal-cli
synced 2025-09-02 04:20:38 +00:00
Merge branch 'master' of https://github.com/AsamK/signal-cli
This commit is contained in:
commit
2e52a7ffd5
47 changed files with 434 additions and 37 deletions
6
.idea/codeStyles/Project.xml
generated
6
.idea/codeStyles/Project.xml
generated
|
@ -15,5 +15,11 @@
|
||||||
<option name="KEEP_BLANK_LINES_BEFORE_RBRACE" value="1" />
|
<option name="KEEP_BLANK_LINES_BEFORE_RBRACE" value="1" />
|
||||||
<option name="BLANK_LINES_AFTER_CLASS_HEADER" value="1" />
|
<option name="BLANK_LINES_AFTER_CLASS_HEADER" value="1" />
|
||||||
</codeStyleSettings>
|
</codeStyleSettings>
|
||||||
|
<codeStyleSettings language="XML">
|
||||||
|
<option name="FORCE_REARRANGE_MODE" value="0" />
|
||||||
|
<arrangement>
|
||||||
|
<rules />
|
||||||
|
</arrangement>
|
||||||
|
</codeStyleSettings>
|
||||||
</code_scheme>
|
</code_scheme>
|
||||||
</component>
|
</component>
|
|
@ -20,8 +20,8 @@ repositories {
|
||||||
}
|
}
|
||||||
|
|
||||||
dependencies {
|
dependencies {
|
||||||
compile 'com.github.turasa:signal-service-java:2.13.8_unofficial_1'
|
compile 'com.github.turasa:signal-service-java:2.13.9_unofficial_1'
|
||||||
compile 'org.bouncycastle:bcprov-jdk15on:1.62'
|
compile 'org.bouncycastle:bcprov-jdk15on:1.64'
|
||||||
compile 'net.sourceforge.argparse4j:argparse4j:0.8.1'
|
compile 'net.sourceforge.argparse4j:argparse4j:0.8.1'
|
||||||
compile 'org.freedesktop.dbus:dbus-java:2.7.0'
|
compile 'org.freedesktop.dbus:dbus-java:2.7.0'
|
||||||
}
|
}
|
||||||
|
|
|
@ -208,6 +208,38 @@ number::
|
||||||
Specify the safety number or fingerprint of the key, only use this option if you have verified
|
Specify the safety number or fingerprint of the key, only use this option if you have verified
|
||||||
the fingerprint.
|
the fingerprint.
|
||||||
|
|
||||||
|
updateProfile
|
||||||
|
--------------
|
||||||
|
Update the name and/or avatar image visible by message recipients for the current users.
|
||||||
|
The profile is stored encrypted on the Signal servers. The decryption key is sent
|
||||||
|
with every outgoing messages (excluding group messages).
|
||||||
|
|
||||||
|
*--name*::
|
||||||
|
New name visible by message recipients.
|
||||||
|
|
||||||
|
*--avatar*::
|
||||||
|
Path to the new avatar visible by message recipients.
|
||||||
|
|
||||||
|
*--remove-avatar*::
|
||||||
|
Remove the avatar visible by message recipients.
|
||||||
|
|
||||||
|
updateContact
|
||||||
|
--------------
|
||||||
|
Update the info associated to a number on our contact list. This change is only
|
||||||
|
local but can be synchronized to other devices by using `sendContacts` (see
|
||||||
|
below).
|
||||||
|
If the contact doesn't exist yet, it will be added.
|
||||||
|
|
||||||
|
NUMBER::
|
||||||
|
Specify the contact phone number.
|
||||||
|
|
||||||
|
*-n*, *--name*::
|
||||||
|
Specify the new name for this contact.
|
||||||
|
|
||||||
|
sendContacts
|
||||||
|
------------
|
||||||
|
Send a synchronization message with the local contacts list to all linked devices.
|
||||||
|
This command should only be used if this is the master device.
|
||||||
|
|
||||||
daemon
|
daemon
|
||||||
~~~~~~
|
~~~~~~
|
||||||
|
|
|
@ -1,6 +1,11 @@
|
||||||
package org.asamk.signal;
|
package org.asamk.signal;
|
||||||
|
|
||||||
import org.whispersystems.signalservice.api.messages.calls.*;
|
import org.whispersystems.signalservice.api.messages.calls.AnswerMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.BusyMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.HangupMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.IceUpdateMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.OfferMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.SignalServiceCallMessage;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,11 @@ import org.asamk.Signal;
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.freedesktop.dbus.DBusConnection;
|
import org.freedesktop.dbus.DBusConnection;
|
||||||
import org.freedesktop.dbus.exceptions.DBusException;
|
import org.freedesktop.dbus.exceptions.DBusException;
|
||||||
import org.whispersystems.signalservice.api.messages.*;
|
import org.whispersystems.signalservice.api.messages.SignalServiceAttachment;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceContent;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceDataMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceEnvelope;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceGroup;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
|
@ -7,6 +7,7 @@ import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||||
import com.fasterxml.jackson.databind.node.ObjectNode;
|
import com.fasterxml.jackson.databind.node.ObjectNode;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.whispersystems.signalservice.api.messages.SignalServiceContent;
|
import org.whispersystems.signalservice.api.messages.SignalServiceContent;
|
||||||
import org.whispersystems.signalservice.api.messages.SignalServiceEnvelope;
|
import org.whispersystems.signalservice.api.messages.SignalServiceEnvelope;
|
||||||
|
|
|
@ -2,9 +2,6 @@ package org.asamk.signal;
|
||||||
|
|
||||||
import org.whispersystems.signalservice.api.messages.multidevice.SentTranscriptMessage;
|
import org.whispersystems.signalservice.api.messages.multidevice.SentTranscriptMessage;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
class JsonSyncDataMessage extends JsonDataMessage {
|
class JsonSyncDataMessage extends JsonDataMessage {
|
||||||
|
|
||||||
String destination;
|
String destination;
|
||||||
|
|
|
@ -18,9 +18,19 @@ package org.asamk.signal;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.ArgumentParsers;
|
import net.sourceforge.argparse4j.ArgumentParsers;
|
||||||
import net.sourceforge.argparse4j.impl.Arguments;
|
import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
import net.sourceforge.argparse4j.inf.*;
|
import net.sourceforge.argparse4j.inf.ArgumentParser;
|
||||||
|
import net.sourceforge.argparse4j.inf.ArgumentParserException;
|
||||||
|
import net.sourceforge.argparse4j.inf.MutuallyExclusiveGroup;
|
||||||
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
import net.sourceforge.argparse4j.inf.Subparsers;
|
||||||
|
|
||||||
import org.asamk.Signal;
|
import org.asamk.Signal;
|
||||||
import org.asamk.signal.commands.*;
|
import org.asamk.signal.commands.Command;
|
||||||
|
import org.asamk.signal.commands.Commands;
|
||||||
|
import org.asamk.signal.commands.DbusCommand;
|
||||||
|
import org.asamk.signal.commands.ExtendedDbusCommand;
|
||||||
|
import org.asamk.signal.commands.LocalCommand;
|
||||||
import org.asamk.signal.manager.BaseConfig;
|
import org.asamk.signal.manager.BaseConfig;
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.asamk.signal.util.IOUtils;
|
import org.asamk.signal.util.IOUtils;
|
||||||
|
|
|
@ -5,9 +5,27 @@ import org.asamk.signal.storage.contacts.ContactInfo;
|
||||||
import org.asamk.signal.storage.groups.GroupInfo;
|
import org.asamk.signal.storage.groups.GroupInfo;
|
||||||
import org.asamk.signal.util.DateUtils;
|
import org.asamk.signal.util.DateUtils;
|
||||||
import org.asamk.signal.util.Util;
|
import org.asamk.signal.util.Util;
|
||||||
import org.whispersystems.signalservice.api.messages.*;
|
import org.whispersystems.signalservice.api.messages.SignalServiceAttachment;
|
||||||
import org.whispersystems.signalservice.api.messages.calls.*;
|
import org.whispersystems.signalservice.api.messages.SignalServiceAttachmentPointer;
|
||||||
import org.whispersystems.signalservice.api.messages.multidevice.*;
|
import org.whispersystems.signalservice.api.messages.SignalServiceContent;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceDataMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceEnvelope;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceGroup;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceReceiptMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceTypingMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.AnswerMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.BusyMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.HangupMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.IceUpdateMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.OfferMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.calls.SignalServiceCallMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.BlockedListMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.ConfigurationMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.ContactsMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.ReadMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.SentTranscriptMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.VerifiedMessage;
|
||||||
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.whispersystems.libsignal.InvalidKeyException;
|
import org.whispersystems.libsignal.InvalidKeyException;
|
||||||
|
|
||||||
|
|
|
@ -20,11 +20,14 @@ public class Commands {
|
||||||
addCommand("removeDevice", new RemoveDeviceCommand());
|
addCommand("removeDevice", new RemoveDeviceCommand());
|
||||||
addCommand("removePin", new RemovePinCommand());
|
addCommand("removePin", new RemovePinCommand());
|
||||||
addCommand("send", new SendCommand());
|
addCommand("send", new SendCommand());
|
||||||
|
addCommand("sendContacts", new SendContactsCommand());
|
||||||
|
addCommand("updateContact", new UpdateContactCommand());
|
||||||
addCommand("setPin", new SetPinCommand());
|
addCommand("setPin", new SetPinCommand());
|
||||||
addCommand("trust", new TrustCommand());
|
addCommand("trust", new TrustCommand());
|
||||||
addCommand("unregister", new UnregisterCommand());
|
addCommand("unregister", new UnregisterCommand());
|
||||||
addCommand("updateAccount", new UpdateAccountCommand());
|
addCommand("updateAccount", new UpdateAccountCommand());
|
||||||
addCommand("updateGroup", new UpdateGroupCommand());
|
addCommand("updateGroup", new UpdateGroupCommand());
|
||||||
|
addCommand("updateProfile", new UpdateProfileCommand());
|
||||||
addCommand("verify", new VerifyCommand());
|
addCommand("verify", new VerifyCommand());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,7 @@ package org.asamk.signal.commands;
|
||||||
import net.sourceforge.argparse4j.impl.Arguments;
|
import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.DbusReceiveMessageHandler;
|
import org.asamk.signal.DbusReceiveMessageHandler;
|
||||||
import org.asamk.signal.JsonDbusReceiveMessageHandler;
|
import org.asamk.signal.JsonDbusReceiveMessageHandler;
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package org.asamk.signal.commands;
|
package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
|
|
||||||
import org.asamk.Signal;
|
import org.asamk.Signal;
|
||||||
|
|
||||||
public interface DbusCommand extends Command {
|
public interface DbusCommand extends Command {
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package org.asamk.signal.commands;
|
package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
|
|
||||||
import org.asamk.Signal;
|
import org.asamk.Signal;
|
||||||
import org.freedesktop.dbus.DBusConnection;
|
import org.freedesktop.dbus.DBusConnection;
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.UserAlreadyExists;
|
import org.asamk.signal.UserAlreadyExists;
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.whispersystems.libsignal.InvalidKeyException;
|
import org.whispersystems.libsignal.InvalidKeyException;
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.asamk.signal.util.DateUtils;
|
import org.asamk.signal.util.DateUtils;
|
||||||
import org.whispersystems.signalservice.api.messages.multidevice.DeviceInfo;
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceInfo;
|
||||||
|
|
|
@ -3,6 +3,7 @@ package org.asamk.signal.commands;
|
||||||
import net.sourceforge.argparse4j.impl.Arguments;
|
import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.asamk.signal.storage.groups.GroupInfo;
|
import org.asamk.signal.storage.groups.GroupInfo;
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.asamk.signal.storage.protocol.JsonIdentityKeyStore;
|
import org.asamk.signal.storage.protocol.JsonIdentityKeyStore;
|
||||||
import org.asamk.signal.util.Hex;
|
import org.asamk.signal.util.Hex;
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package org.asamk.signal.commands;
|
package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
||||||
public interface LocalCommand extends Command {
|
public interface LocalCommand extends Command {
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.GroupIdFormatException;
|
import org.asamk.signal.GroupIdFormatException;
|
||||||
import org.asamk.signal.GroupNotFoundException;
|
import org.asamk.signal.GroupNotFoundException;
|
||||||
import org.asamk.signal.NotAGroupMemberException;
|
import org.asamk.signal.NotAGroupMemberException;
|
||||||
|
@ -11,7 +12,12 @@ import org.whispersystems.signalservice.api.push.exceptions.EncapsulatedExceptio
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
||||||
import static org.asamk.signal.util.ErrorUtils.*;
|
import static org.asamk.signal.util.ErrorUtils.handleAssertionError;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleEncapsulatedExceptions;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleGroupIdFormatException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleGroupNotFoundException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleIOException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleNotAGroupMemberException;
|
||||||
|
|
||||||
public class QuitGroupCommand implements LocalCommand {
|
public class QuitGroupCommand implements LocalCommand {
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,7 @@ package org.asamk.signal.commands;
|
||||||
import net.sourceforge.argparse4j.impl.Arguments;
|
import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.Signal;
|
import org.asamk.Signal;
|
||||||
import org.asamk.signal.JsonReceiveMessageHandler;
|
import org.asamk.signal.JsonReceiveMessageHandler;
|
||||||
import org.asamk.signal.ReceiveMessageHandler;
|
import org.asamk.signal.ReceiveMessageHandler;
|
||||||
|
|
|
@ -3,6 +3,7 @@ package org.asamk.signal.commands;
|
||||||
import net.sourceforge.argparse4j.impl.Arguments;
|
import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.whispersystems.libsignal.util.guava.Optional;
|
import org.whispersystems.libsignal.util.guava.Optional;
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,7 @@ package org.asamk.signal.commands;
|
||||||
import net.sourceforge.argparse4j.impl.Arguments;
|
import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.Signal;
|
import org.asamk.Signal;
|
||||||
import org.asamk.signal.AttachmentInvalidException;
|
import org.asamk.signal.AttachmentInvalidException;
|
||||||
import org.asamk.signal.GroupIdFormatException;
|
import org.asamk.signal.GroupIdFormatException;
|
||||||
|
@ -18,7 +19,13 @@ import java.nio.charset.Charset;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import static org.asamk.signal.util.ErrorUtils.*;
|
import static org.asamk.signal.util.ErrorUtils.handleAssertionError;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleDBusExecutionException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleEncapsulatedExceptions;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleGroupIdFormatException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleGroupNotFoundException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleIOException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleNotAGroupMemberException;
|
||||||
|
|
||||||
public class SendCommand implements DbusCommand {
|
public class SendCommand implements DbusCommand {
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,31 @@
|
||||||
|
package org.asamk.signal.commands;
|
||||||
|
|
||||||
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
import org.asamk.signal.manager.Manager;
|
||||||
|
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
public class SendContactsCommand implements LocalCommand {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void attachToSubparser(final Subparser subparser) {
|
||||||
|
subparser.help("Send a synchronization message with the local contacts list to all linked devices.");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int handleCommand(final Namespace ns, final Manager m) {
|
||||||
|
if (!m.isRegistered()) {
|
||||||
|
System.err.println("User is not registered.");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
m.sendContacts();
|
||||||
|
return 0;
|
||||||
|
} catch (IOException | UntrustedIdentityException e) {
|
||||||
|
System.err.println("SendContacts error: " + e.getMessage());
|
||||||
|
return 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.whispersystems.libsignal.util.guava.Optional;
|
import org.whispersystems.libsignal.util.guava.Optional;
|
||||||
|
|
||||||
|
|
|
@ -4,6 +4,7 @@ import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
import net.sourceforge.argparse4j.inf.MutuallyExclusiveGroup;
|
import net.sourceforge.argparse4j.inf.MutuallyExclusiveGroup;
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.asamk.signal.util.Hex;
|
import org.asamk.signal.util.Hex;
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
|
@ -0,0 +1,34 @@
|
||||||
|
package org.asamk.signal.commands;
|
||||||
|
|
||||||
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
||||||
|
public class UpdateContactCommand implements LocalCommand {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void attachToSubparser(final Subparser subparser) {
|
||||||
|
subparser.addArgument("number")
|
||||||
|
.help("Contact number");
|
||||||
|
subparser.addArgument("-n", "--name")
|
||||||
|
.required(true)
|
||||||
|
.help("New contact name");
|
||||||
|
subparser.help("Update the details of a given contact");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int handleCommand(final Namespace ns, final Manager m) {
|
||||||
|
if (!m.isRegistered()) {
|
||||||
|
System.err.println("User is not registered.");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
String number = ns.getString("number");
|
||||||
|
String name = ns.getString("name");
|
||||||
|
|
||||||
|
m.setContactName(number, name);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.Signal;
|
import org.asamk.Signal;
|
||||||
import org.asamk.signal.AttachmentInvalidException;
|
import org.asamk.signal.AttachmentInvalidException;
|
||||||
import org.asamk.signal.GroupIdFormatException;
|
import org.asamk.signal.GroupIdFormatException;
|
||||||
|
@ -15,7 +16,11 @@ import java.io.IOException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import static org.asamk.signal.util.ErrorUtils.*;
|
import static org.asamk.signal.util.ErrorUtils.handleEncapsulatedExceptions;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleGroupIdFormatException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleGroupNotFoundException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleIOException;
|
||||||
|
import static org.asamk.signal.util.ErrorUtils.handleNotAGroupMemberException;
|
||||||
|
|
||||||
public class UpdateGroupCommand implements DbusCommand {
|
public class UpdateGroupCommand implements DbusCommand {
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,73 @@
|
||||||
|
package org.asamk.signal.commands;
|
||||||
|
|
||||||
|
import net.sourceforge.argparse4j.impl.Arguments;
|
||||||
|
import net.sourceforge.argparse4j.inf.MutuallyExclusiveGroup;
|
||||||
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
|
import org.asamk.signal.manager.Manager;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
public class UpdateProfileCommand implements LocalCommand {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void attachToSubparser(final Subparser subparser) {
|
||||||
|
final MutuallyExclusiveGroup avatarOptions = subparser.addMutuallyExclusiveGroup();
|
||||||
|
avatarOptions.addArgument("--avatar")
|
||||||
|
.help("Path to new profile avatar");
|
||||||
|
avatarOptions.addArgument("--remove-avatar")
|
||||||
|
.action(Arguments.storeTrue());
|
||||||
|
|
||||||
|
subparser.addArgument("--name")
|
||||||
|
.help("New profile name");
|
||||||
|
|
||||||
|
subparser.help("Set a name and/or avatar image for the user profile");
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int handleCommand(final Namespace ns, final Manager m) {
|
||||||
|
if (!m.isRegistered()) {
|
||||||
|
System.err.println("User is not registered.");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
String name = ns.getString("name");
|
||||||
|
|
||||||
|
if (name != null) {
|
||||||
|
try {
|
||||||
|
m.setProfileName(name);
|
||||||
|
} catch (IOException e) {
|
||||||
|
System.err.println("UpdateAccount error: " + e.getMessage());
|
||||||
|
return 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
String avatarPath = ns.getString("avatar");
|
||||||
|
|
||||||
|
if (avatarPath != null) {
|
||||||
|
File avatarFile = new File(avatarPath);
|
||||||
|
|
||||||
|
try {
|
||||||
|
m.setProfileAvatar(avatarFile);
|
||||||
|
} catch (IOException e) {
|
||||||
|
System.err.println("UpdateAccount error: " + e.getMessage());
|
||||||
|
return 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
boolean removeAvatar = ns.getBoolean("remove_avatar");
|
||||||
|
|
||||||
|
if (removeAvatar) {
|
||||||
|
try {
|
||||||
|
m.removeProfileAvatar();
|
||||||
|
} catch (IOException e) {
|
||||||
|
System.err.println("UpdateAccount error: " + e.getMessage());
|
||||||
|
return 3;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,6 +2,7 @@ package org.asamk.signal.commands;
|
||||||
|
|
||||||
import net.sourceforge.argparse4j.inf.Namespace;
|
import net.sourceforge.argparse4j.inf.Namespace;
|
||||||
import net.sourceforge.argparse4j.inf.Subparser;
|
import net.sourceforge.argparse4j.inf.Subparser;
|
||||||
|
|
||||||
import org.asamk.signal.manager.Manager;
|
import org.asamk.signal.manager.Manager;
|
||||||
import org.whispersystems.signalservice.internal.push.LockedException;
|
import org.whispersystems.signalservice.internal.push.LockedException;
|
||||||
|
|
||||||
|
|
|
@ -17,7 +17,11 @@
|
||||||
package org.asamk.signal.manager;
|
package org.asamk.signal.manager;
|
||||||
|
|
||||||
import org.asamk.Signal;
|
import org.asamk.Signal;
|
||||||
import org.asamk.signal.*;
|
import org.asamk.signal.AttachmentInvalidException;
|
||||||
|
import org.asamk.signal.GroupNotFoundException;
|
||||||
|
import org.asamk.signal.NotAGroupMemberException;
|
||||||
|
import org.asamk.signal.TrustLevel;
|
||||||
|
import org.asamk.signal.UserAlreadyExists;
|
||||||
import org.asamk.signal.storage.SignalAccount;
|
import org.asamk.signal.storage.SignalAccount;
|
||||||
import org.asamk.signal.storage.contacts.ContactInfo;
|
import org.asamk.signal.storage.contacts.ContactInfo;
|
||||||
import org.asamk.signal.storage.groups.GroupInfo;
|
import org.asamk.signal.storage.groups.GroupInfo;
|
||||||
|
@ -26,8 +30,22 @@ import org.asamk.signal.storage.protocol.JsonIdentityKeyStore;
|
||||||
import org.asamk.signal.storage.threads.ThreadInfo;
|
import org.asamk.signal.storage.threads.ThreadInfo;
|
||||||
import org.asamk.signal.util.IOUtils;
|
import org.asamk.signal.util.IOUtils;
|
||||||
import org.asamk.signal.util.Util;
|
import org.asamk.signal.util.Util;
|
||||||
import org.signal.libsignal.metadata.*;
|
import org.signal.libsignal.metadata.InvalidMetadataMessageException;
|
||||||
import org.whispersystems.libsignal.*;
|
import org.signal.libsignal.metadata.InvalidMetadataVersionException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolDuplicateMessageException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolInvalidKeyException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolInvalidKeyIdException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolInvalidMessageException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolInvalidVersionException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolLegacyMessageException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolNoSessionException;
|
||||||
|
import org.signal.libsignal.metadata.ProtocolUntrustedIdentityException;
|
||||||
|
import org.signal.libsignal.metadata.SelfSendException;
|
||||||
|
import org.whispersystems.libsignal.IdentityKey;
|
||||||
|
import org.whispersystems.libsignal.IdentityKeyPair;
|
||||||
|
import org.whispersystems.libsignal.InvalidKeyException;
|
||||||
|
import org.whispersystems.libsignal.InvalidMessageException;
|
||||||
|
import org.whispersystems.libsignal.InvalidVersionException;
|
||||||
import org.whispersystems.libsignal.ecc.Curve;
|
import org.whispersystems.libsignal.ecc.Curve;
|
||||||
import org.whispersystems.libsignal.ecc.ECKeyPair;
|
import org.whispersystems.libsignal.ecc.ECKeyPair;
|
||||||
import org.whispersystems.libsignal.ecc.ECPublicKey;
|
import org.whispersystems.libsignal.ecc.ECPublicKey;
|
||||||
|
@ -44,8 +62,26 @@ import org.whispersystems.signalservice.api.crypto.SignalServiceCipher;
|
||||||
import org.whispersystems.signalservice.api.crypto.UnidentifiedAccess;
|
import org.whispersystems.signalservice.api.crypto.UnidentifiedAccess;
|
||||||
import org.whispersystems.signalservice.api.crypto.UnidentifiedAccessPair;
|
import org.whispersystems.signalservice.api.crypto.UnidentifiedAccessPair;
|
||||||
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
import org.whispersystems.signalservice.api.crypto.UntrustedIdentityException;
|
||||||
import org.whispersystems.signalservice.api.messages.*;
|
import org.whispersystems.signalservice.api.messages.SendMessageResult;
|
||||||
import org.whispersystems.signalservice.api.messages.multidevice.*;
|
import org.whispersystems.signalservice.api.messages.SignalServiceAttachment;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceAttachmentPointer;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceAttachmentStream;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceContent;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceDataMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceEnvelope;
|
||||||
|
import org.whispersystems.signalservice.api.messages.SignalServiceGroup;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.ContactsMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceContact;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceContactsInputStream;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceContactsOutputStream;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceGroup;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceGroupsInputStream;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceGroupsOutputStream;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.DeviceInfo;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.RequestMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.SentTranscriptMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.SignalServiceSyncMessage;
|
||||||
|
import org.whispersystems.signalservice.api.messages.multidevice.VerifiedMessage;
|
||||||
import org.whispersystems.signalservice.api.push.ContactTokenDetails;
|
import org.whispersystems.signalservice.api.push.ContactTokenDetails;
|
||||||
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
||||||
import org.whispersystems.signalservice.api.push.exceptions.AuthorizationFailedException;
|
import org.whispersystems.signalservice.api.push.exceptions.AuthorizationFailedException;
|
||||||
|
@ -54,17 +90,35 @@ import org.whispersystems.signalservice.api.push.exceptions.NetworkFailureExcept
|
||||||
import org.whispersystems.signalservice.api.push.exceptions.UnregisteredUserException;
|
import org.whispersystems.signalservice.api.push.exceptions.UnregisteredUserException;
|
||||||
import org.whispersystems.signalservice.api.util.InvalidNumberException;
|
import org.whispersystems.signalservice.api.util.InvalidNumberException;
|
||||||
import org.whispersystems.signalservice.api.util.SleepTimer;
|
import org.whispersystems.signalservice.api.util.SleepTimer;
|
||||||
|
import org.whispersystems.signalservice.api.util.StreamDetails;
|
||||||
import org.whispersystems.signalservice.api.util.UptimeSleepTimer;
|
import org.whispersystems.signalservice.api.util.UptimeSleepTimer;
|
||||||
import org.whispersystems.signalservice.internal.push.SignalServiceProtos;
|
import org.whispersystems.signalservice.internal.push.SignalServiceProtos;
|
||||||
import org.whispersystems.signalservice.internal.push.UnsupportedDataMessageException;
|
import org.whispersystems.signalservice.internal.push.UnsupportedDataMessageException;
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
||||||
import java.io.*;
|
import java.io.File;
|
||||||
|
import java.io.FileInputStream;
|
||||||
|
import java.io.FileNotFoundException;
|
||||||
|
import java.io.FileOutputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.OutputStream;
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
import java.nio.file.Files;
|
import java.nio.file.Files;
|
||||||
import java.nio.file.Paths;
|
import java.nio.file.Paths;
|
||||||
import java.nio.file.StandardCopyOption;
|
import java.nio.file.StandardCopyOption;
|
||||||
import java.util.*;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.LinkedList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Locale;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Objects;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
import java.util.concurrent.TimeoutException;
|
import java.util.concurrent.TimeoutException;
|
||||||
|
|
||||||
|
@ -204,6 +258,20 @@ public class Manager implements Signal {
|
||||||
accountManager.setAccountAttributes(account.getSignalingKey(), account.getSignalProtocolStore().getLocalRegistrationId(), true, account.getRegistrationLockPin(), getSelfUnidentifiedAccessKey(), false);
|
accountManager.setAccountAttributes(account.getSignalingKey(), account.getSignalProtocolStore().getLocalRegistrationId(), true, account.getRegistrationLockPin(), getSelfUnidentifiedAccessKey(), false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void setProfileName(String name) throws IOException {
|
||||||
|
accountManager.setProfileName(account.getProfileKey(), name);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setProfileAvatar(File avatar) throws IOException {
|
||||||
|
final StreamDetails streamDetails = Utils.createStreamDetailsFromFile(avatar);
|
||||||
|
accountManager.setProfileAvatar(account.getProfileKey(), streamDetails);
|
||||||
|
streamDetails.getStream().close();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void removeProfileAvatar() throws IOException {
|
||||||
|
accountManager.setProfileAvatar(account.getProfileKey(), null);
|
||||||
|
}
|
||||||
|
|
||||||
public void unregister() throws IOException {
|
public void unregister() throws IOException {
|
||||||
// When setting an empty GCM id, the Signal-Server also sets the fetchesMessages property to false.
|
// When setting an empty GCM id, the Signal-Server also sets the fetchesMessages property to false.
|
||||||
// If this is the master device, other users can't send messages to this number anymore.
|
// If this is the master device, other users can't send messages to this number anymore.
|
||||||
|
@ -564,6 +632,7 @@ public class Manager implements Signal {
|
||||||
if (attachments != null) {
|
if (attachments != null) {
|
||||||
messageBuilder.withAttachments(Utils.getSignalServiceAttachments(attachments));
|
messageBuilder.withAttachments(Utils.getSignalServiceAttachments(attachments));
|
||||||
}
|
}
|
||||||
|
messageBuilder.withProfileKey(account.getProfileKey());
|
||||||
sendMessageLegacy(messageBuilder, recipients);
|
sendMessageLegacy(messageBuilder, recipients);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1347,7 +1416,7 @@ public class Manager implements Signal {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void sendContacts() throws IOException, UntrustedIdentityException {
|
public void sendContacts() throws IOException, UntrustedIdentityException {
|
||||||
File contactsFile = IOUtils.createTempFile();
|
File contactsFile = IOUtils.createTempFile();
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -15,14 +15,30 @@ import org.whispersystems.signalservice.api.messages.SignalServiceEnvelope;
|
||||||
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
import org.whispersystems.signalservice.api.push.SignalServiceAddress;
|
||||||
import org.whispersystems.signalservice.api.util.InvalidNumberException;
|
import org.whispersystems.signalservice.api.util.InvalidNumberException;
|
||||||
import org.whispersystems.signalservice.api.util.PhoneNumberFormatter;
|
import org.whispersystems.signalservice.api.util.PhoneNumberFormatter;
|
||||||
|
import org.whispersystems.signalservice.api.util.StreamDetails;
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
||||||
import java.io.*;
|
import java.io.DataInputStream;
|
||||||
|
import java.io.DataOutputStream;
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileInputStream;
|
||||||
|
import java.io.FileNotFoundException;
|
||||||
|
import java.io.FileOutputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.io.UnsupportedEncodingException;
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
import java.net.URLDecoder;
|
import java.net.URLDecoder;
|
||||||
import java.net.URLEncoder;
|
import java.net.URLEncoder;
|
||||||
import java.nio.file.Files;
|
import java.nio.file.Files;
|
||||||
import java.util.*;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
import static org.whispersystems.signalservice.internal.util.Util.isEmpty;
|
import static org.whispersystems.signalservice.internal.util.Util.isEmpty;
|
||||||
|
|
||||||
|
@ -53,7 +69,18 @@ class Utils {
|
||||||
// TODO mabybe add a parameter to set the voiceNote, preview, width, height and caption option
|
// TODO mabybe add a parameter to set the voiceNote, preview, width, height and caption option
|
||||||
Optional<byte[]> preview = Optional.absent();
|
Optional<byte[]> preview = Optional.absent();
|
||||||
Optional<String> caption = Optional.absent();
|
Optional<String> caption = Optional.absent();
|
||||||
return new SignalServiceAttachmentStream(attachmentStream, mime, attachmentSize, Optional.of(attachmentFile.getName()), false, preview, 0, 0, caption, null);
|
Optional<String> blurHash = Optional.absent();
|
||||||
|
return new SignalServiceAttachmentStream(attachmentStream, mime, attachmentSize, Optional.of(attachmentFile.getName()), false, preview, 0, 0, caption, blurHash, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
static StreamDetails createStreamDetailsFromFile(File file) throws IOException {
|
||||||
|
InputStream stream = new FileInputStream(file);
|
||||||
|
final long size = file.length();
|
||||||
|
String mime = Files.probeContentType(file.toPath());
|
||||||
|
if (mime == null) {
|
||||||
|
mime = "application/octet-stream";
|
||||||
|
}
|
||||||
|
return new StreamDetails(stream, mime, size);
|
||||||
}
|
}
|
||||||
|
|
||||||
static CertificateValidator getCertificateValidator() {
|
static CertificateValidator getCertificateValidator() {
|
||||||
|
|
|
@ -9,6 +9,7 @@ import com.fasterxml.jackson.databind.JsonNode;
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||||
import com.fasterxml.jackson.databind.node.ObjectNode;
|
import com.fasterxml.jackson.databind.node.ObjectNode;
|
||||||
|
|
||||||
import org.asamk.signal.storage.contacts.JsonContactsStore;
|
import org.asamk.signal.storage.contacts.JsonContactsStore;
|
||||||
import org.asamk.signal.storage.groups.JsonGroupStore;
|
import org.asamk.signal.storage.groups.JsonGroupStore;
|
||||||
import org.asamk.signal.storage.protocol.JsonSignalProtocolStore;
|
import org.asamk.signal.storage.protocol.JsonSignalProtocolStore;
|
||||||
|
@ -139,7 +140,9 @@ public class SignalAccount {
|
||||||
if (node != null) {
|
if (node != null) {
|
||||||
deviceId = node.asInt();
|
deviceId = node.asInt();
|
||||||
}
|
}
|
||||||
if (rootNode.has("isMultiDevice")) isMultiDevice = Util.getNotNullNode(rootNode, "isMultiDevice").asBoolean();
|
if (rootNode.has("isMultiDevice")) {
|
||||||
|
isMultiDevice = Util.getNotNullNode(rootNode, "isMultiDevice").asBoolean();
|
||||||
|
}
|
||||||
username = Util.getNotNullNode(rootNode, "username").asText();
|
username = Util.getNotNullNode(rootNode, "username").asText();
|
||||||
password = Util.getNotNullNode(rootNode, "password").asText();
|
password = Util.getNotNullNode(rootNode, "password").asText();
|
||||||
JsonNode pinNode = rootNode.get("registrationLockPin");
|
JsonNode pinNode = rootNode.get("registrationLockPin");
|
||||||
|
|
|
@ -3,7 +3,12 @@ package org.asamk.signal.storage.contacts;
|
||||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||||
import com.fasterxml.jackson.core.JsonGenerator;
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
import com.fasterxml.jackson.core.JsonParser;
|
import com.fasterxml.jackson.core.JsonParser;
|
||||||
import com.fasterxml.jackson.databind.*;
|
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||||
|
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||||
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
||||||
|
|
||||||
|
|
|
@ -3,9 +3,15 @@ package org.asamk.signal.storage.groups;
|
||||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||||
import com.fasterxml.jackson.core.JsonGenerator;
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
import com.fasterxml.jackson.core.JsonParser;
|
import com.fasterxml.jackson.core.JsonParser;
|
||||||
import com.fasterxml.jackson.databind.*;
|
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||||
|
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||||
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
||||||
|
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
|
@ -2,7 +2,12 @@ package org.asamk.signal.storage.protocol;
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonGenerator;
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
import com.fasterxml.jackson.core.JsonParser;
|
import com.fasterxml.jackson.core.JsonParser;
|
||||||
import com.fasterxml.jackson.databind.*;
|
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||||
|
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||||
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
|
|
||||||
import org.asamk.signal.TrustLevel;
|
import org.asamk.signal.TrustLevel;
|
||||||
import org.whispersystems.libsignal.IdentityKey;
|
import org.whispersystems.libsignal.IdentityKey;
|
||||||
import org.whispersystems.libsignal.IdentityKeyPair;
|
import org.whispersystems.libsignal.IdentityKeyPair;
|
||||||
|
@ -12,7 +17,11 @@ import org.whispersystems.libsignal.state.IdentityKeyStore;
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.*;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
public class JsonIdentityKeyStore implements IdentityKeyStore {
|
public class JsonIdentityKeyStore implements IdentityKeyStore {
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,12 @@ package org.asamk.signal.storage.protocol;
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonGenerator;
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
import com.fasterxml.jackson.core.JsonParser;
|
import com.fasterxml.jackson.core.JsonParser;
|
||||||
import com.fasterxml.jackson.databind.*;
|
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||||
|
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||||
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
|
|
||||||
import org.whispersystems.libsignal.InvalidKeyIdException;
|
import org.whispersystems.libsignal.InvalidKeyIdException;
|
||||||
import org.whispersystems.libsignal.state.PreKeyRecord;
|
import org.whispersystems.libsignal.state.PreKeyRecord;
|
||||||
import org.whispersystems.libsignal.state.PreKeyStore;
|
import org.whispersystems.libsignal.state.PreKeyStore;
|
||||||
|
|
|
@ -2,14 +2,23 @@ package org.asamk.signal.storage.protocol;
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonGenerator;
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
import com.fasterxml.jackson.core.JsonParser;
|
import com.fasterxml.jackson.core.JsonParser;
|
||||||
import com.fasterxml.jackson.databind.*;
|
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||||
|
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||||
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
|
|
||||||
import org.whispersystems.libsignal.SignalProtocolAddress;
|
import org.whispersystems.libsignal.SignalProtocolAddress;
|
||||||
import org.whispersystems.libsignal.state.SessionRecord;
|
import org.whispersystems.libsignal.state.SessionRecord;
|
||||||
import org.whispersystems.libsignal.state.SessionStore;
|
import org.whispersystems.libsignal.state.SessionStore;
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.*;
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.LinkedList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
class JsonSessionStore implements SessionStore {
|
class JsonSessionStore implements SessionStore {
|
||||||
|
|
||||||
|
|
|
@ -3,6 +3,7 @@ package org.asamk.signal.storage.protocol;
|
||||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
||||||
|
|
||||||
import org.asamk.signal.TrustLevel;
|
import org.asamk.signal.TrustLevel;
|
||||||
import org.whispersystems.libsignal.IdentityKey;
|
import org.whispersystems.libsignal.IdentityKey;
|
||||||
import org.whispersystems.libsignal.IdentityKeyPair;
|
import org.whispersystems.libsignal.IdentityKeyPair;
|
||||||
|
|
|
@ -2,7 +2,12 @@ package org.asamk.signal.storage.protocol;
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonGenerator;
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
import com.fasterxml.jackson.core.JsonParser;
|
import com.fasterxml.jackson.core.JsonParser;
|
||||||
import com.fasterxml.jackson.databind.*;
|
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||||
|
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||||
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
|
|
||||||
import org.whispersystems.libsignal.InvalidKeyIdException;
|
import org.whispersystems.libsignal.InvalidKeyIdException;
|
||||||
import org.whispersystems.libsignal.state.SignedPreKeyRecord;
|
import org.whispersystems.libsignal.state.SignedPreKeyRecord;
|
||||||
import org.whispersystems.libsignal.state.SignedPreKeyStore;
|
import org.whispersystems.libsignal.state.SignedPreKeyStore;
|
||||||
|
|
|
@ -3,7 +3,12 @@ package org.asamk.signal.storage.threads;
|
||||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||||
import com.fasterxml.jackson.core.JsonGenerator;
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
import com.fasterxml.jackson.core.JsonParser;
|
import com.fasterxml.jackson.core.JsonParser;
|
||||||
import com.fasterxml.jackson.databind.*;
|
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||||
|
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||||
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
||||||
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
||||||
|
|
||||||
|
|
|
@ -12,7 +12,9 @@ import java.nio.file.attribute.PosixFilePermissions;
|
||||||
import java.util.EnumSet;
|
import java.util.EnumSet;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
import static java.nio.file.attribute.PosixFilePermission.*;
|
import static java.nio.file.attribute.PosixFilePermission.OWNER_EXECUTE;
|
||||||
|
import static java.nio.file.attribute.PosixFilePermission.OWNER_READ;
|
||||||
|
import static java.nio.file.attribute.PosixFilePermission.OWNER_WRITE;
|
||||||
|
|
||||||
public class IOUtils {
|
public class IOUtils {
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package org.asamk.signal.util;
|
package org.asamk.signal.util;
|
||||||
|
|
||||||
import com.fasterxml.jackson.databind.JsonNode;
|
import com.fasterxml.jackson.databind.JsonNode;
|
||||||
|
|
||||||
import org.asamk.signal.GroupIdFormatException;
|
import org.asamk.signal.GroupIdFormatException;
|
||||||
import org.whispersystems.signalservice.internal.util.Base64;
|
import org.whispersystems.signalservice.internal.util.Base64;
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue