diff --git a/web/sidebar/community-drawer.css b/web/sidebar/community-drawer.css
new file mode 100644
--- /dev/null
+++ b/web/sidebar/community-drawer.css
@@ -0,0 +1,10 @@
+.container {
+  background-color: var(--drawer-bg);
+  display: flex;
+  overflow-y: auto;
+  flex-direction: column;
+  padding-right: 8px;
+  padding-top: 8px;
+  padding-bottom: 8px;
+  align-self: flex-start;
+}
diff --git a/web/sidebar/community-drawer.react.js b/web/sidebar/community-drawer.react.js
new file mode 100644
--- /dev/null
+++ b/web/sidebar/community-drawer.react.js
@@ -0,0 +1,67 @@
+// @flow
+
+import * as React from 'react';
+
+import {
+  childThreadInfos,
+  communityThreadSelector,
+} from 'lib/selectors/thread-selectors.js';
+import {
+  createRecursiveDrawerItemsData,
+  appendSuffix,
+} from 'lib/utils/drawer-utils.react.js';
+import { useResolvedThreadInfos } from 'lib/utils/entity-helpers.js';
+
+import CommunityDrawerItemCommunity from './community-drawer-item-community.react.js';
+import css from './community-drawer.css';
+import { ThreadListProvider } from '../chat/thread-list-provider.js';
+import { useSelector } from '../redux/redux-utils.js';
+
+const maxDepth = 2;
+const labelStyles = ['titleLevel0', 'titleLevel1', 'titleLevel2'];
+
+function CommunityDrawer(): React.Node {
+  const childThreadInfosMap = useSelector(childThreadInfos);
+  const communities = useSelector(communityThreadSelector);
+  const resolvedCommunities = useResolvedThreadInfos(communities);
+  const communitiesSuffixed = React.useMemo(
+    () => appendSuffix(resolvedCommunities),
+    [resolvedCommunities],
+  );
+
+  const drawerItemsData = createRecursiveDrawerItemsData(
+    childThreadInfosMap,
+    communitiesSuffixed,
+    labelStyles,
+    maxDepth,
+  );
+
+  const [openCommunity, setOpenCommunity] = React.useState(
+    communitiesSuffixed.length === 1 ? communitiesSuffixed[0].id : null,
+  );
+
+  const setOpenCommunityOrClose = React.useCallback((communityID: string) => {
+    setOpenCommunity(open => (open === communityID ? null : communityID));
+  }, []);
+
+  const communitiesComponents = React.useMemo(
+    () =>
+      drawerItemsData.map(item => (
+        <CommunityDrawerItemCommunity
+          itemData={item}
+          key={item.threadInfo.id}
+          toggleExpanded={setOpenCommunityOrClose}
+          expanded={item.threadInfo.id === openCommunity}
+        />
+      )),
+    [drawerItemsData, openCommunity, setOpenCommunityOrClose],
+  );
+
+  return (
+    <ThreadListProvider>
+      <div className={css.container}>{communitiesComponents}</div>
+    </ThreadListProvider>
+  );
+}
+
+export default CommunityDrawer;
diff --git a/web/theme.css b/web/theme.css
--- a/web/theme.css
+++ b/web/theme.css
@@ -198,4 +198,5 @@
   --drawer-expand-button-disabled: var(--shades-black-80);
   --drawer-item-color: var(--shades-white-60);
   --drawer-open-community-bg: #191919;
+  --drawer-bg: var(--shades-black-90);
 }