1 package org
.asamk
.signal
.commands
;
3 import net
.sourceforge
.argparse4j
.impl
.Arguments
;
4 import net
.sourceforge
.argparse4j
.inf
.Namespace
;
5 import net
.sourceforge
.argparse4j
.inf
.Subparser
;
7 import org
.asamk
.signal
.JsonWriter
;
8 import org
.asamk
.signal
.OutputWriter
;
9 import org
.asamk
.signal
.PlainTextWriter
;
10 import org
.asamk
.signal
.commands
.exceptions
.CommandException
;
11 import org
.asamk
.signal
.commands
.exceptions
.UnexpectedErrorException
;
12 import org
.asamk
.signal
.commands
.exceptions
.UserErrorException
;
13 import org
.asamk
.signal
.manager
.AttachmentInvalidException
;
14 import org
.asamk
.signal
.manager
.Manager
;
15 import org
.asamk
.signal
.manager
.api
.Message
;
16 import org
.asamk
.signal
.manager
.api
.RecipientIdentifier
;
17 import org
.asamk
.signal
.manager
.groups
.GroupNotFoundException
;
18 import org
.asamk
.signal
.manager
.groups
.GroupSendingNotAllowedException
;
19 import org
.asamk
.signal
.manager
.groups
.NotAGroupMemberException
;
20 import org
.asamk
.signal
.util
.CommandUtil
;
21 import org
.asamk
.signal
.util
.ErrorUtils
;
22 import org
.asamk
.signal
.util
.IOUtils
;
23 import org
.slf4j
.Logger
;
24 import org
.slf4j
.LoggerFactory
;
26 import java
.io
.IOException
;
27 import java
.nio
.charset
.Charset
;
28 import java
.util
.List
;
30 import java
.util
.stream
.Collectors
;
32 public class SendCommand
implements JsonRpcLocalCommand
{
34 private final static Logger logger
= LoggerFactory
.getLogger(SendCommand
.class);
37 public String
getName() {
42 public void attachToSubparser(final Subparser subparser
) {
43 subparser
.help("Send a message to another user or group.");
44 subparser
.addArgument("recipient").help("Specify the recipients' phone number.").nargs("*");
45 subparser
.addArgument("-g", "--group-id", "--group").help("Specify the recipient group ID.").nargs("*");
46 subparser
.addArgument("--note-to-self")
47 .help("Send the message to self without notification.")
48 .action(Arguments
.storeTrue());
50 subparser
.addArgument("-m", "--message").help("Specify the message, if missing standard input is used.");
51 subparser
.addArgument("-a", "--attachment").nargs("*").help("Add file as attachment");
52 subparser
.addArgument("-e", "--end-session", "--endsession")
53 .help("Clear session state and send end session message.")
54 .action(Arguments
.storeTrue());
58 public void handleCommand(
59 final Namespace ns
, final Manager m
, final OutputWriter outputWriter
60 ) throws CommandException
{
61 final var isNoteToSelf
= Boolean
.TRUE
.equals(ns
.getBoolean("note-to-self"));
62 final var recipientStrings
= ns
.<String
>getList("recipient");
63 final var groupIdStrings
= ns
.<String
>getList("group-id");
65 final var recipientIdentifiers
= CommandUtil
.getRecipientIdentifiers(m
,
70 final var isEndSession
= Boolean
.TRUE
.equals(ns
.getBoolean("end-session"));
72 final var singleRecipients
= recipientIdentifiers
.stream()
73 .filter(r
-> r
instanceof RecipientIdentifier
.Single
)
74 .map(RecipientIdentifier
.Single
.class::cast
)
75 .collect(Collectors
.toSet());
76 if (singleRecipients
.isEmpty()) {
77 throw new UserErrorException("No recipients given");
81 m
.sendEndSessionMessage(singleRecipients
);
83 } catch (IOException e
) {
84 throw new UnexpectedErrorException("Failed to send message: " + e
.getMessage() + " (" + e
.getClass()
85 .getSimpleName() + ")", e
);
89 var messageText
= ns
.getString("message");
90 if (messageText
== null) {
92 messageText
= IOUtils
.readAll(System
.in, Charset
.defaultCharset());
93 } catch (IOException e
) {
94 throw new UserErrorException("Failed to read message from stdin: " + e
.getMessage());
98 List
<String
> attachments
= ns
.getList("attachment");
99 if (attachments
== null) {
100 attachments
= List
.of();
104 var results
= m
.sendMessage(new Message(messageText
, attachments
), recipientIdentifiers
);
105 outputResult(outputWriter
, results
.getTimestamp());
106 ErrorUtils
.handleSendMessageResults(results
.getResults());
107 } catch (AttachmentInvalidException
| IOException e
) {
108 throw new UnexpectedErrorException("Failed to send message: " + e
.getMessage() + " (" + e
.getClass()
109 .getSimpleName() + ")", e
);
110 } catch (GroupNotFoundException
| NotAGroupMemberException
| GroupSendingNotAllowedException e
) {
111 throw new UserErrorException(e
.getMessage());
115 private void outputResult(final OutputWriter outputWriter
, final long timestamp
) {
116 if (outputWriter
instanceof PlainTextWriter
) {
117 final var writer
= (PlainTextWriter
) outputWriter
;
118 writer
.println("{}", timestamp
);
120 final var writer
= (JsonWriter
) outputWriter
;
121 writer
.write(Map
.of("timestamp", timestamp
));