Skip to content

Channel Detail Views

The Channel Detail plugin ships five built-in views, one per default section of ChannelDetail. Each view is a SectionNavigator section content component — it receives the current layout and reads the active channel from ChannelDetailContext — and most are paired with a dedicated search/pagination hook backed by a stream-chat search source.

View Section Purpose
ChannelManagementView Channel info Channel info with edit mode, membership state, and channel actions.
ChannelMembersView Members Browse, add, and remove members; per-member detail.
PinnedMessagesView Pinned messages Paginated list of pinned messages.
ChannelMediaView Photos & videos Grid of shared images and videos.
ChannelFilesView Files Shared files and audio grouped by month.

All views are exported from stream-chat-react/channel-detail. Override a view by passing a replacement SectionContent in a custom sections array.

ChannelManagementView

Renders channel information with a read (view) mode and an edit mode, the channel's membership state, and a set of channel-level actions gated behind confirmation dialogs (mute channel, mute user, block user, leave channel, delete chat).

Props

Name Description Type Default
layout Provided by SectionNavigator. "tabs" | "inline" -
ViewModeComponent Body rendered in read mode. React.ComponentType<ChannelManagementInfoBodyProps> ChannelManagementInfoBody
EditModeComponent Body rendered in edit mode. React.ComponentType<ChannelManagementEditBodyProps> ChannelManagementEditBody
uploadImage Handler that uploads a selected channel image and returns its URL. (file: File) => Promise<string> | string -
channelManagementActionSet The ordered set of channel actions to render. ChannelManagementActionItem[] defaultChannelManagementActionSet

A ChannelManagementActionItem is { type, Component }, where type is one of "muteChannel", "muteUser", "blockUser", "leaveChannel", "deleteChat" (or a custom string). The default components are available as DefaultChannelManagementActions so you can reorder or wrap them:

import {
  ChannelManagementView,
  DefaultChannelManagementActions,
} from "stream-chat-react/channel-detail";

const channelManagementActionSet = [
  {
    type: "muteChannel",
    Component: DefaultChannelManagementActions.MuteChannel,
  },
  {
    type: "leaveChannel",
    Component: DefaultChannelManagementActions.LeaveChannel,
  },
];

ChannelMembersView

A mode-driven view: it renders a member list (browse), an add-members flow (add), and a per-member detail (memberDetail). The browse and memberDetail modes are handled internally; every other mode — the built-in add or any app-provided mode — is resolved from the modeViews registry.

Props

Name Description Type Default
layout Provided by SectionNavigator. "tabs" | "inline" -
headerActionSet Ordered set of header actions (e.g. add members). ChannelMembersHeaderActionItem[] default set
HeaderActions Component that renders the header actions. React.ComponentType<ChannelMembersHeaderActionsProps> default
HeaderActionsMenuTrigger Trigger for the header actions overflow menu. React.ComponentType<ChannelMembersHeaderActionsMenuTriggerProps> default
modeViews App-provided modes, merged with (and overriding) the built-in ones. ChannelMembersViewModes defaultChannelMembersModeViews

A mode is { Title, Body }, keyed by the mode string passed to modeController.setMode. The mode's Body receives a modeController ({ mode, setMode }) it uses to navigate between modes:

import { ChannelMembersView } from "stream-chat-react/channel-detail";

const modeViews = {
  bulkRemove: {
    Title: () => <>Remove members</>,
    Body: ({ modeController }) => (
      <BulkRemove onDone={() => modeController.setMode("browse")} />
    ),
  },
};

<ChannelMembersView modeViews={modeViews} />;

The two built-in mode views are exported so you can reuse or wrap them in a custom modeViews registry:

  • ChannelMembersBrowseView — the browse member list. Accepts an optional onMemberSelect(member) callback.
  • ChannelMembersAddView — the add flow. Receives the modeController and accepts an optional searchSource (UserSearchSource) to override how users are searched.

ChannelMemberDetail

The per-member detail (the memberDetail mode) renders member actions — send message, mute/unmute, block/unblock, remove — as a ChannelMemberActionItem[] ({ type, Component }, where type is "sendMessage" | "muteUser" | "blockUser" | "removeUser" or a custom string). The defaults are exported as DefaultChannelMemberActions and defaultChannelMemberActionSet.

PinnedMessagesView, ChannelMediaView, ChannelFilesView

ChannelMediaView and ChannelFilesView take only the section content layout prop (SectionNavigatorSectionContentProps); they read the channel from context and paginate through dedicated hooks. PinnedMessagesView additionally accepts an optional searchSource (MessageSearchSource) so you can supply a preconfigured search source. Customize them by replacing the view component or by composing their search hooks into your own UI.

View Search hook Notes
PinnedMessagesView usePinnedMessagesSearch Paginated pinned messages with custom timestamp formatting.
ChannelMediaView useChannelMediaSearch Images/videos grid with avatars and video durations.
ChannelFilesView useChannelFilesSearch Files and audio grouped by month with type-specific icons.

Search & pagination hooks

Each list view is backed by a hook that wraps a stream-chat search source and exposes the items, loading state, and the source for pagination. They are exported so you can build custom list UIs:

Hook Returns (selected fields)
useChannelMediaSearch { mediaItems, channelMediaSearchSource, hasResultsLoaded, isLoading }
useChannelFilesSearch Files search source, items, and loading state (mirrors the media hook).
useChannelMembersSearch { displayedMembers, membersSearchSource, hasMembers, handleSearchChange, resetMembersSearch, searchInputResetKey }
usePinnedMessagesSearch { displayedMessages, pinnedMessagesSearchSource, hasPinnedMessages, hasSearchResultsLoaded, handleSearchChange }

usePinnedMessagesSearch accepts an optional { searchSource } (UsePinnedMessagesSearchParams). When you pass your own MessageSearchSource, it is used as-is — its filters and sort are respected. Otherwise the hook builds one scoped to the channel with a pinned: true filter and text $autocomplete matching.

import { useChannelMediaSearch } from "stream-chat-react/channel-detail";

const CustomMediaGrid = () => {
  const { mediaItems, isLoading, hasResultsLoaded } = useChannelMediaSearch();
  if (isLoading && !hasResultsLoaded) return <Spinner />;
  return <Grid items={mediaItems} />;
};

These hooks must be used within ChannelDetail (or a ChannelDetailProvider), since they resolve the active channel from useChannelDetailContext.

Media & files data transforms

The media and files views build their lists from two pure helpers that flatten an array of messages into render-ready items. They are exported so you can derive the same item shapes when building a fully custom grid or list outside the view components:

Helper Signature Returns
toChannelMediaItems (messages: Array<MessageResponse | LocalMessage>) => ChannelMediaItem[] One item per renderable image/video attachment, each carrying a galleryItem descriptor, stable id, type, optional durationSeconds, and the posting user.
toChannelFileSections (messages: Array<MessageResponse | LocalMessage>) => ChannelFileSections File/audio attachments flattened into a single ChannelFileSections object ({ groupCounts, items, sections }) shaped for GroupedVirtuoso: a flat items array grouped contiguously into descending month/year sections ({ key, timestamp }), with groupCounts aligned 1:1 to the sections. The raw attachment is kept untransformed.

The attachment types each helper recognizes are exported as constants: MEDIA_ATTACHMENT_TYPES (['image', 'video']) and FILE_ATTACHMENT_TYPES (['file', 'audio']), along with the ChannelMediaItem, ChannelMediaItemType, ChannelFileItem, ChannelFileSection, ChannelFileSections, and ChannelFileAttachmentType types.

import { toChannelMediaItems } from "stream-chat-react/channel-detail";

const items = toChannelMediaItems(messages);