Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
49 changes: 49 additions & 0 deletions docs/stream-cli_chat_mute-channel.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
## stream-cli chat mute-channel

Mute a channel for a user

### Synopsis

Mutes a channel for a specific user. Muted channels do not trigger notifications,
affect unread counts, or unhide themselves when new messages are added.

You can optionally set an expiration time for the mute using the --expiration flag,
such as '1h', '24h', etc.


```
stream-cli chat mute-channel --type [channel-type] --id [channel-id] --user-id [user-id] [--expiration duration] [flags]
```

### Examples

```
# Mute a channel indefinitely for user 'john'
$ stream-cli chat mute-channel --type messaging --id redteam --user-id john

# Mute a channel for 6 hours
$ stream-cli chat mute-channel --type messaging --id redteam --user-id john --expiration 6h

```

### Options

```
--expiration string [optional] Expiration duration (e.g., '1h', '6h')
-h, --help help for mute-channel
-i, --id string [required] Channel ID
-t, --type string [required] Channel type such as 'messaging'
-u, --user-id string [required] User ID
```

### Options inherited from parent commands

```
--app string [optional] Application name to use as it's defined in the configuration file
--config string [optional] Explicit config file path
```

### SEE ALSO

* [stream-cli chat](stream-cli_chat.md) - Allows you to interact with your Chat applications

64 changes: 64 additions & 0 deletions pkg/cmd/chat/channel/channel.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package channel
import (
"encoding/json"
"errors"
"fmt"
"time"

stream "github.com/GetStream/stream-chat-go/v5"
Expand All @@ -28,6 +29,7 @@ func NewCmds() []*cobra.Command {
assignRoleCmd(),
hideCmd(),
showCmd(),
muteChannelCmd(),
}
}

Expand Down Expand Up @@ -610,3 +612,65 @@ func showCmd() *cobra.Command {

return cmd
}

func muteChannelCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "mute-channel --type [channel-type] --id [channel-id] --user-id [user-id] [--expiration duration]",
Short: "Mute a channel for a user",
Long: heredoc.Doc(`
Mutes a channel for a specific user. Muted channels do not trigger notifications,
affect unread counts, or unhide themselves when new messages are added.

You can optionally set an expiration time for the mute using the --expiration flag,
such as '1h', '24h', etc.
`),
Example: heredoc.Doc(`
# Mute a channel indefinitely for user 'john'
$ stream-cli chat mute-channel --type messaging --id redteam --user-id john

# Mute a channel for 6 hours
$ stream-cli chat mute-channel --type messaging --id redteam --user-id john --expiration 6h
`),
RunE: func(cmd *cobra.Command, args []string) error {
client, err := config.GetConfig(cmd).GetClient(cmd)
if err != nil {
return err
}

typ, _ := cmd.Flags().GetString("type")
id, _ := cmd.Flags().GetString("id")
user, _ := cmd.Flags().GetString("user-id")
expStr, _ := cmd.Flags().GetString("expiration")

var exp *time.Duration
if expStr != "" {
d, err := time.ParseDuration(expStr)
if err != nil {
return fmt.Errorf("invalid expiration duration: %w", err)
}
exp = &d
}

ch := client.Channel(typ, id)
_, err = ch.Mute(cmd.Context(), user, exp)
if err != nil {
return err
}

cmd.Printf("Successfully muted channel [%s] for user [%s]\n", id, user)
return nil
},
}

fl := cmd.Flags()
fl.StringP("type", "t", "", "[required] Channel type such as 'messaging'")
fl.StringP("id", "i", "", "[required] Channel ID")
fl.StringP("user-id", "u", "", "[required] User ID")
fl.String("expiration", "", "[optional] Expiration duration (e.g., '1h', '6h')")

_ = cmd.MarkFlagRequired("type")
_ = cmd.MarkFlagRequired("id")
_ = cmd.MarkFlagRequired("user-id")

return cmd
}
36 changes: 36 additions & 0 deletions pkg/cmd/chat/channel/channel_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -204,3 +204,39 @@ func TestHideAndShowChannel(t *testing.T) {
require.NoError(t, err)
require.Contains(t, cmd.OutOrStdout().(*bytes.Buffer).String(), "Successfully shown channel")
}

func TestMuteChannel(t *testing.T) {
cmd := test.GetRootCmdWithSubCommands(NewCmds()...)
ch := test.InitChannel(t)
u := test.CreateUser()

t.Cleanup(func() {
test.DeleteChannel(ch)
test.DeleteUser(u)
})

// Add user to channel so mute works
cmd.SetArgs([]string{"add-members", "-t", "messaging", "-i", ch, u})
_, err := cmd.ExecuteC()
require.NoError(t, err)

// Mute the channel for the user
cmd.SetArgs([]string{"mute-channel", "-t", "messaging", "-i", ch, "-u", u})
_, err = cmd.ExecuteC()
require.NoError(t, err)

// Check that output contains success message
out := cmd.OutOrStdout().(*bytes.Buffer).String()
require.Contains(t, out, "Successfully muted channel")

// OPTIONAL: Verify via SDK that user mute exists
client := test.InitClient()
ctx := context.Background()
userResp, err := client.QueryUsers(ctx, &stream.QueryOption{
Filter: map[string]interface{}{"id": u},
})
require.NoError(t, err)
require.Len(t, userResp.Users, 1)
require.NotEmpty(t, userResp.Users[0].ChannelMutes)
require.Equal(t, ch, userResp.Users[0].ChannelMutes[0].Channel.ID)
}