terminal: edit and delete messages for everyone on the chat (#497)
This commit is contained in:
committed by
GitHub
parent
4247dc4271
commit
c14f692b68
@@ -364,6 +364,15 @@ processChatCommand = \case
|
||||
quotedItemId <- withStore $ \st -> getDirectChatItemIdByText st userId contactId msgDir (safeDecodeUtf8 quotedMsg)
|
||||
let mc = MCText $ safeDecodeUtf8 msg
|
||||
processChatCommand $ APISendMessageQuote CTDirect contactId quotedItemId mc
|
||||
DeleteMessage cName deletedMsg -> withUser $ \User {userId} -> do
|
||||
contactId <- withStore $ \st -> getContactIdByName st userId cName
|
||||
deletedItemId <- withStore $ \st -> getDirectChatItemIdByText st userId contactId SMDSnd (safeDecodeUtf8 deletedMsg)
|
||||
processChatCommand $ APIDeleteChatItem CTDirect contactId deletedItemId CIDMBroadcast
|
||||
EditMessage cName editedMsg msg -> withUser $ \User {userId} -> do
|
||||
contactId <- withStore $ \st -> getContactIdByName st userId cName
|
||||
editedItemId <- withStore $ \st -> getDirectChatItemIdByText st userId contactId SMDSnd (safeDecodeUtf8 editedMsg)
|
||||
let mc = MCText $ safeDecodeUtf8 msg
|
||||
processChatCommand $ APIUpdateChatItem CTDirect contactId editedItemId mc
|
||||
NewGroup gProfile -> withUser $ \user -> do
|
||||
gVar <- asks idsDrg
|
||||
CRGroupCreated <$> withStore (\st -> createNewGroup st gVar user gProfile)
|
||||
@@ -444,6 +453,15 @@ processChatCommand = \case
|
||||
quotedItemId <- withStore $ \st -> getGroupChatItemIdByText st user groupId cName (safeDecodeUtf8 quotedMsg)
|
||||
let mc = MCText $ safeDecodeUtf8 msg
|
||||
processChatCommand $ APISendMessageQuote CTGroup groupId quotedItemId mc
|
||||
DeleteGroupMessage gName deletedMsg -> withUser $ \user@User {localDisplayName} -> do
|
||||
groupId <- withStore $ \st -> getGroupIdByName st user gName
|
||||
deletedItemId <- withStore $ \st -> getGroupChatItemIdByText st user groupId (Just localDisplayName) (safeDecodeUtf8 deletedMsg)
|
||||
processChatCommand $ APIDeleteChatItem CTGroup groupId deletedItemId CIDMBroadcast
|
||||
EditGroupMessage gName editedMsg msg -> withUser $ \user@User {localDisplayName} -> do
|
||||
groupId <- withStore $ \st -> getGroupIdByName st user gName
|
||||
editedItemId <- withStore $ \st -> getGroupChatItemIdByText st user groupId (Just localDisplayName) (safeDecodeUtf8 editedMsg)
|
||||
let mc = MCText $ safeDecodeUtf8 msg
|
||||
processChatCommand $ APIUpdateChatItem CTGroup groupId editedItemId mc
|
||||
SendFile cName f -> withUser $ \user@User {userId} -> withChatLock $ do
|
||||
(fileSize, chSize) <- checkSndFile f
|
||||
contact <- withStore $ \st -> getContactByName st userId cName
|
||||
@@ -1650,7 +1668,7 @@ chatCommandP =
|
||||
<|> ("/help files" <|> "/help file" <|> "/hf") $> ChatHelp HSFiles
|
||||
<|> ("/help groups" <|> "/help group" <|> "/hg") $> ChatHelp HSGroups
|
||||
<|> ("/help address" <|> "/ha") $> ChatHelp HSMyAddress
|
||||
<|> ("/help replies" <|> "/hr") $> ChatHelp HSQuotes
|
||||
<|> ("/help messages" <|> "/hm") $> ChatHelp HSMessages
|
||||
<|> ("/help" <|> "/h") $> ChatHelp HSMain
|
||||
<|> ("/group #" <|> "/group " <|> "/g #" <|> "/g ") *> (NewGroup <$> groupProfile)
|
||||
<|> ("/add #" <|> "/add " <|> "/a #" <|> "/a ") *> (AddMember <$> displayName <* A.space <*> displayName <*> memberRole)
|
||||
@@ -1663,6 +1681,8 @@ chatCommandP =
|
||||
<|> A.char '#' *> (SendGroupMessage <$> displayName <* A.space <*> A.takeByteString)
|
||||
<|> (">#" <|> "> #") *> (SendGroupMessageQuote <$> displayName <* A.space <*> pure Nothing <*> quotedMsg <*> A.takeByteString)
|
||||
<|> (">#" <|> "> #") *> (SendGroupMessageQuote <$> displayName <* A.space <* optional (A.char '@') <*> (Just <$> displayName) <* A.space <*> quotedMsg <*> A.takeByteString)
|
||||
<|> ("\\#" <|> "\\ #") *> (DeleteGroupMessage <$> displayName <* A.space <*> A.takeByteString)
|
||||
<|> ("!#" <|> "! #") *> (EditGroupMessage <$> displayName <* A.space <*> quotedMsg <*> A.takeByteString)
|
||||
<|> ("/contacts" <|> "/cs") $> ListContacts
|
||||
<|> ("/connect " <|> "/c ") *> (Connect <$> ((Just <$> strP) <|> A.takeByteString $> Nothing))
|
||||
<|> ("/connect" <|> "/c") $> AddContact
|
||||
@@ -1670,6 +1690,8 @@ chatCommandP =
|
||||
<|> A.char '@' *> (SendMessage <$> displayName <* A.space <*> A.takeByteString)
|
||||
<|> (">@" <|> "> @") *> sendMsgQuote (AMsgDirection SMDRcv)
|
||||
<|> (">>@" <|> ">> @") *> sendMsgQuote (AMsgDirection SMDSnd)
|
||||
<|> ("\\@" <|> "\\ @") *> (DeleteMessage <$> displayName <* A.space <*> A.takeByteString)
|
||||
<|> ("!@" <|> "! @") *> (EditMessage <$> displayName <* A.space <*> quotedMsg <*> A.takeByteString)
|
||||
<|> "/feed " *> (SendMessageBroadcast <$> A.takeByteString)
|
||||
<|> ("/file #" <|> "/f #") *> (SendGroupFile <$> displayName <* A.space <*> filePath)
|
||||
<|> ("/file @" <|> "/file " <|> "/f @" <|> "/f ") *> (SendFile <$> displayName <* A.space <*> filePath)
|
||||
|
||||
@@ -79,7 +79,7 @@ data ChatController = ChatController
|
||||
config :: ChatConfig
|
||||
}
|
||||
|
||||
data HelpSection = HSMain | HSFiles | HSGroups | HSMyAddress | HSMarkdown | HSQuotes
|
||||
data HelpSection = HSMain | HSFiles | HSGroups | HSMyAddress | HSMarkdown | HSMessages
|
||||
deriving (Show, Generic)
|
||||
|
||||
instance ToJSON HelpSection where
|
||||
@@ -120,6 +120,8 @@ data ChatCommand
|
||||
| SendMessage ContactName ByteString
|
||||
| SendMessageQuote {contactName :: ContactName, msgDir :: AMsgDirection, quotedMsg :: ByteString, message :: ByteString}
|
||||
| SendMessageBroadcast ByteString
|
||||
| DeleteMessage ContactName ByteString
|
||||
| EditMessage {contactName :: ContactName, editedMsg :: ByteString, message :: ByteString}
|
||||
| NewGroup GroupProfile
|
||||
| AddMember GroupName ContactName GroupMemberRole
|
||||
| JoinGroup GroupName
|
||||
@@ -131,6 +133,8 @@ data ChatCommand
|
||||
| ListGroups
|
||||
| SendGroupMessage GroupName ByteString
|
||||
| SendGroupMessageQuote {groupName :: GroupName, contactName_ :: Maybe ContactName, quotedMsg :: ByteString, message :: ByteString}
|
||||
| DeleteGroupMessage GroupName ByteString
|
||||
| EditGroupMessage {groupName :: ContactName, editedMsg :: ByteString, message :: ByteString}
|
||||
| SendFile ContactName FilePath
|
||||
| SendGroupFile GroupName FilePath
|
||||
| ReceiveFile FileTransferId (Maybe FilePath)
|
||||
|
||||
@@ -7,7 +7,7 @@ module Simplex.Chat.Help
|
||||
filesHelpInfo,
|
||||
groupsHelpInfo,
|
||||
myAddressHelpInfo,
|
||||
quotesHelpInfo,
|
||||
messagesHelpInfo,
|
||||
markdownInfo,
|
||||
)
|
||||
where
|
||||
@@ -83,7 +83,7 @@ chatHelpInfo =
|
||||
green "Create your address: " <> highlight "/address",
|
||||
"",
|
||||
green "Other commands:",
|
||||
indent <> highlight "/help <topic> " <> " - help on: files, groups, address, replies, smp_servers",
|
||||
indent <> highlight "/help <topic> " <> " - help on: messages, files, groups, address",
|
||||
indent <> highlight "/profile " <> " - show / update user profile",
|
||||
indent <> highlight "/delete <contact>" <> " - delete contact and all messages with them",
|
||||
indent <> highlight "/contacts " <> " - list contacts",
|
||||
@@ -143,8 +143,8 @@ myAddressHelpInfo =
|
||||
"The commands may be abbreviated: " <> listHighlight ["/ad", "/da", "/sa", "/ac", "/rc"]
|
||||
]
|
||||
|
||||
quotesHelpInfo :: [StyledString]
|
||||
quotesHelpInfo =
|
||||
messagesHelpInfo :: [StyledString]
|
||||
messagesHelpInfo =
|
||||
map
|
||||
styleMarkdown
|
||||
[ green "Sending replies to messages",
|
||||
@@ -152,7 +152,17 @@ quotesHelpInfo =
|
||||
indent <> highlight "> @alice (hi) <msg> " <> " - to reply to alice's most recent message",
|
||||
indent <> highlight ">> @alice (hi) <msg> " <> " - to quote user's most recent message to alice",
|
||||
indent <> highlight "> #team (hi) <msg> " <> " - to quote most recent message in the group from any member",
|
||||
indent <> highlight "> #team @alice (hi) <msg>" <> " - to quote alice's most recent message in the group #team"
|
||||
indent <> highlight "> #team @alice (hi) <msg>" <> " - to quote alice's most recent message in the group #team",
|
||||
"",
|
||||
green "Deleting sent messages (for everyone)",
|
||||
"To delete a message that starts with \"hi\":",
|
||||
indent <> highlight "\\ @alice hi " <> " - to delete your message to alice",
|
||||
indent <> highlight "\\ #team hi " <> " - to delete your message in the group #team",
|
||||
"",
|
||||
green "Editing sent messages",
|
||||
"To edit a message that starts with \"hi\":",
|
||||
indent <> highlight "! @alice (hi) <new msg> " <> " - to edit your message to alice",
|
||||
indent <> highlight "! #team (hi) <new msg> " <> " - to edit your message in the group #team"
|
||||
]
|
||||
|
||||
markdownInfo :: [StyledString]
|
||||
|
||||
@@ -101,9 +101,9 @@ updateTermState ac tw (key, ms) ts@TerminalState {inputString = s, inputPosition
|
||||
_ -> ts
|
||||
where
|
||||
insertCharsWithContact cs
|
||||
| null s && cs /= "@" && cs /= "#" && cs /= "/" && cs /= ">" =
|
||||
| null s && cs /= "@" && cs /= "#" && cs /= "/" && cs /= ">" && cs /= "\\" && cs /= "!" =
|
||||
insertChars $ contactPrefix <> cs
|
||||
| s == ">" && cs == " " =
|
||||
| (s == ">" || s == "\\" || s == "!") && cs == " " =
|
||||
insertChars $ cs <> contactPrefix
|
||||
| otherwise = insertChars cs
|
||||
insertChars = ts' . if p >= length s then append else insert
|
||||
|
||||
@@ -60,7 +60,7 @@ responseToView testView = \case
|
||||
HSFiles -> filesHelpInfo
|
||||
HSGroups -> groupsHelpInfo
|
||||
HSMyAddress -> myAddressHelpInfo
|
||||
HSQuotes -> quotesHelpInfo
|
||||
HSMessages -> messagesHelpInfo
|
||||
HSMarkdown -> markdownInfo
|
||||
CRWelcome user -> chatWelcome user
|
||||
CRContactsList cs -> viewContactsList cs
|
||||
@@ -207,7 +207,7 @@ viewItemUpdate chat ChatItem {chatDir, meta, content, quotedItem} = case chat of
|
||||
where
|
||||
from = ttyFromContactEdited c
|
||||
quote = maybe [] (directQuote chatDir) quotedItem
|
||||
CIDirectSnd -> ["item updated"]
|
||||
CIDirectSnd -> ["message updated"]
|
||||
GroupChat g -> case chatDir of
|
||||
CIGroupRcv GroupMember {localDisplayName = m} -> case content of
|
||||
CIRcvMsgContent mc -> viewReceivedMessage from quote meta mc
|
||||
@@ -215,7 +215,7 @@ viewItemUpdate chat ChatItem {chatDir, meta, content, quotedItem} = case chat of
|
||||
where
|
||||
from = ttyFromGroupEdited g m
|
||||
quote = maybe [] (groupQuote g) quotedItem
|
||||
CIGroupSnd -> ["item updated"]
|
||||
CIGroupSnd -> ["message updated"]
|
||||
_ -> []
|
||||
|
||||
viewItemDelete :: ChatInfo c -> ChatItem c d -> ChatItem c' d' -> [StyledString]
|
||||
@@ -223,14 +223,14 @@ viewItemDelete chat ChatItem {chatDir, meta, content = deletedContent} ChatItem
|
||||
DirectChat Contact {localDisplayName = c} -> case (chatDir, deletedContent, toContent) of
|
||||
(CIDirectRcv, CIRcvMsgContent mc, CIRcvDeleted mode) -> case mode of
|
||||
CIDMBroadcast -> viewReceivedMessage (ttyFromContactDeleted c) [] meta mc
|
||||
CIDMInternal -> ["item deleted"]
|
||||
(CIDirectSnd, _, _) -> ["item deleted"]
|
||||
CIDMInternal -> ["message deleted"]
|
||||
(CIDirectSnd, _, _) -> ["message deleted"]
|
||||
_ -> []
|
||||
GroupChat g -> case (chatDir, deletedContent, toContent) of
|
||||
(CIGroupRcv GroupMember {localDisplayName = m}, CIRcvMsgContent mc, CIRcvDeleted mode) -> case mode of
|
||||
CIDMBroadcast -> viewReceivedMessage (ttyFromGroupDeleted g m) [] meta mc
|
||||
CIDMInternal -> ["item deleted"]
|
||||
(CIGroupSnd, _, _) -> ["item deleted"]
|
||||
CIDMInternal -> ["message deleted"]
|
||||
(CIGroupSnd, _, _) -> ["message deleted"]
|
||||
_ -> []
|
||||
_ -> []
|
||||
|
||||
|
||||
@@ -174,7 +174,7 @@ testDirectMessageUpdate =
|
||||
alice #$> ("/_get chat @2 count=100", chat', [((1, "hello 🙂"), Nothing), ((0, "hi alice"), Just (1, "hello 🙂"))])
|
||||
bob #$> ("/_get chat @2 count=100", chat', [((0, "hello 🙂"), Nothing), ((1, "hi alice"), Just (0, "hello 🙂"))])
|
||||
|
||||
alice #$> ("/_update item @2 1 text hey 👋", id, "item updated")
|
||||
alice #$> ("/_update item @2 1 text hey 👋", id, "message updated")
|
||||
bob <# "alice> [edited] hey 👋"
|
||||
|
||||
alice #$> ("/_get chat @2 count=100", chat', [((1, "hey 👋"), Nothing), ((0, "hi alice"), Just (1, "hello 🙂"))])
|
||||
@@ -190,7 +190,7 @@ testDirectMessageUpdate =
|
||||
alice #$> ("/_get chat @2 count=100", chat', [((1, "hey 👋"), Nothing), ((0, "hi alice"), Just (1, "hello 🙂")), ((0, "hey alice"), Just (1, "hey 👋"))])
|
||||
bob #$> ("/_get chat @2 count=100", chat', [((0, "hey 👋"), Nothing), ((1, "hi alice"), Just (0, "hello 🙂")), ((1, "hey alice"), Just (0, "hey 👋"))])
|
||||
|
||||
alice #$> ("/_update item @2 1 text greetings 🤝", id, "item updated")
|
||||
alice #$> ("/_update item @2 1 text greetings 🤝", id, "message updated")
|
||||
bob <# "alice> [edited] greetings 🤝"
|
||||
|
||||
alice #$> ("/_update item @2 2 text updating bob's message", id, "cannot update this item")
|
||||
@@ -198,11 +198,11 @@ testDirectMessageUpdate =
|
||||
alice #$> ("/_get chat @2 count=100", chat', [((1, "greetings 🤝"), Nothing), ((0, "hi alice"), Just (1, "hello 🙂")), ((0, "hey alice"), Just (1, "hey 👋"))])
|
||||
bob #$> ("/_get chat @2 count=100", chat', [((0, "greetings 🤝"), Nothing), ((1, "hi alice"), Just (0, "hello 🙂")), ((1, "hey alice"), Just (0, "hey 👋"))])
|
||||
|
||||
bob #$> ("/_update item @2 2 text hey Alice", id, "item updated")
|
||||
bob #$> ("/_update item @2 2 text hey Alice", id, "message updated")
|
||||
alice <# "bob> [edited] > hello 🙂"
|
||||
alice <## " hey Alice"
|
||||
|
||||
bob #$> ("/_update item @2 3 text greetings Alice", id, "item updated")
|
||||
bob #$> ("/_update item @2 3 text greetings Alice", id, "message updated")
|
||||
alice <# "bob> [edited] > hey 👋"
|
||||
alice <## " greetings Alice"
|
||||
|
||||
@@ -226,8 +226,8 @@ testDirectMessageDelete =
|
||||
alice <# "bob> > hello 🙂"
|
||||
alice <## " hey alic"
|
||||
|
||||
alice #$> ("/_delete item @2 1 internal", id, "item deleted")
|
||||
alice #$> ("/_delete item @2 2 internal", id, "item deleted")
|
||||
alice #$> ("/_delete item @2 1 internal", id, "message deleted")
|
||||
alice #$> ("/_delete item @2 2 internal", id, "message deleted")
|
||||
|
||||
alice #$$> ("/_get chats", [("@bob", "")])
|
||||
alice #$> ("/_get chat @2 count=100", chat, [])
|
||||
@@ -235,7 +235,7 @@ testDirectMessageDelete =
|
||||
alice #$> ("/_update item @2 1 text updating deleted message", id, "cannot update this item")
|
||||
alice #$> ("/_send_quote @2 1 text quoting deleted message", id, "cannot reply to this message")
|
||||
|
||||
bob #$> ("/_update item @2 2 text hey alice", id, "item updated")
|
||||
bob #$> ("/_update item @2 2 text hey alice", id, "message updated")
|
||||
alice <# "bob> [edited] hey alice"
|
||||
|
||||
alice #$$> ("/_get chats", [("@bob", "hey alice")])
|
||||
@@ -245,14 +245,14 @@ testDirectMessageDelete =
|
||||
bob #> "@alice how are you?"
|
||||
alice <# "bob> how are you?"
|
||||
|
||||
bob #$> ("/_delete item @2 3 broadcast", id, "item deleted")
|
||||
bob #$> ("/_delete item @2 3 broadcast", id, "message deleted")
|
||||
alice <# "bob> [deleted] how are you?"
|
||||
|
||||
alice #$> ("/_delete item @2 1 broadcast", id, "item deleted")
|
||||
alice #$> ("/_delete item @2 1 broadcast", id, "message deleted")
|
||||
bob <# "alice> [deleted] hello 🙂"
|
||||
|
||||
alice #$> ("/_delete item @2 2 broadcast", id, "cannot delete this item")
|
||||
alice #$> ("/_delete item @2 2 internal", id, "item deleted")
|
||||
alice #$> ("/_delete item @2 2 internal", id, "message deleted")
|
||||
|
||||
alice #$$> ("/_get chats", [("@bob", "this item is deleted (broadcast)")])
|
||||
alice #$> ("/_get chat @2 count=100", chat, [(0, "this item is deleted (broadcast)")])
|
||||
@@ -752,7 +752,7 @@ testGroupMessageUpdate =
|
||||
(bob <# "#team alice> hello!")
|
||||
(cath <# "#team alice> hello!")
|
||||
|
||||
alice #$> ("/_update item #1 1 text hey 👋", id, "item updated")
|
||||
alice #$> ("/_update item #1 1 text hey 👋", id, "message updated")
|
||||
concurrently_
|
||||
(bob <# "#team alice> [edited] hey 👋")
|
||||
(cath <# "#team alice> [edited] hey 👋")
|
||||
@@ -780,7 +780,7 @@ testGroupMessageUpdate =
|
||||
bob #$> ("/_get chat #1 count=100", chat', [((0, "hey 👋"), Nothing), ((1, "hi alice"), Just (0, "hey 👋"))])
|
||||
cath #$> ("/_get chat #1 count=100", chat', [((0, "hey 👋"), Nothing), ((0, "hi alice"), Just (0, "hey 👋"))])
|
||||
|
||||
alice #$> ("/_update item #1 1 text greetings 🤝", id, "item updated")
|
||||
alice #$> ("/_update item #1 1 text greetings 🤝", id, "message updated")
|
||||
concurrently_
|
||||
(bob <# "#team alice> [edited] greetings 🤝")
|
||||
(cath <# "#team alice> [edited] greetings 🤝")
|
||||
@@ -816,7 +816,7 @@ testGroupMessageDelete =
|
||||
(bob <# "#team alice> hello!")
|
||||
(cath <# "#team alice> hello!")
|
||||
|
||||
alice #$> ("/_delete item #1 1 internal", id, "item deleted")
|
||||
alice #$> ("/_delete item #1 1 internal", id, "message deleted")
|
||||
|
||||
alice #$> ("/_get chat #1 count=100", chat, [])
|
||||
bob #$> ("/_get chat #1 count=100", chat, [(0, "hello!")])
|
||||
@@ -844,18 +844,18 @@ testGroupMessageDelete =
|
||||
bob #$> ("/_get chat #1 count=100", chat', [((0, "hello!"), Nothing), ((1, "hi alic"), Just (0, "hello!"))])
|
||||
cath #$> ("/_get chat #1 count=100", chat', [((0, "hello!"), Nothing), ((0, "hi alic"), Just (0, "hello!"))])
|
||||
|
||||
alice #$> ("/_delete item #1 1 broadcast", id, "item deleted")
|
||||
alice #$> ("/_delete item #1 1 broadcast", id, "message deleted")
|
||||
concurrently_
|
||||
(bob <# "#team alice> [deleted] hello!")
|
||||
(cath <# "#team alice> [deleted] hello!")
|
||||
|
||||
alice #$> ("/_delete item #1 2 internal", id, "item deleted")
|
||||
alice #$> ("/_delete item #1 2 internal", id, "message deleted")
|
||||
|
||||
alice #$> ("/_get chat #1 count=100", chat', [])
|
||||
bob #$> ("/_get chat #1 count=100", chat', [((0, "this item is deleted (broadcast)"), Nothing), ((1, "hi alic"), Just (0, "hello!"))])
|
||||
cath #$> ("/_get chat #1 count=100", chat', [((0, "this item is deleted (broadcast)"), Nothing), ((0, "hi alic"), Just (0, "hello!"))])
|
||||
|
||||
bob #$> ("/_update item #1 2 text hi alice", id, "item updated")
|
||||
bob #$> ("/_update item #1 2 text hi alice", id, "message updated")
|
||||
concurrently_
|
||||
(alice <# "#team bob> [edited] hi alice")
|
||||
( do
|
||||
@@ -874,13 +874,13 @@ testGroupMessageDelete =
|
||||
(alice <# "#team cath> how are you?")
|
||||
(bob <# "#team cath> how are you?")
|
||||
|
||||
cath #$> ("/_delete item #1 3 broadcast", id, "item deleted")
|
||||
cath #$> ("/_delete item #1 3 broadcast", id, "message deleted")
|
||||
concurrently_
|
||||
(alice <# "#team cath> [deleted] how are you?")
|
||||
(bob <# "#team cath> [deleted] how are you?")
|
||||
|
||||
alice #$> ("/_delete item #1 2 broadcast", id, "cannot delete this item")
|
||||
alice #$> ("/_delete item #1 2 internal", id, "item deleted")
|
||||
alice #$> ("/_delete item #1 2 internal", id, "message deleted")
|
||||
|
||||
alice #$> ("/_get chat #1 count=100", chat', [((0, "this item is deleted (broadcast)"), Nothing)])
|
||||
bob #$> ("/_get chat #1 count=100", chat', [((0, "this item is deleted (broadcast)"), Nothing), ((1, "hi alice"), Just (0, "hello!")), ((0, "this item is deleted (broadcast)"), Nothing)])
|
||||
|
||||
Reference in New Issue
Block a user