Skip to content

Commit

Permalink
feat: add collection count
Browse files Browse the repository at this point in the history
  • Loading branch information
navinkarkera committed Oct 8, 2024
1 parent 8e53f79 commit a57cf0e
Show file tree
Hide file tree
Showing 11 changed files with 41 additions and 53 deletions.
17 changes: 8 additions & 9 deletions src/library-authoring/common/context.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import { useToggle } from '@openedx/paragon';
import React from 'react';

import { ContentHit } from '../../search-manager';

Check failure on line 4 in src/library-authoring/common/context.tsx

View workflow job for this annotation

GitHub Actions / tests (20)

More than 1 blank line not allowed
export enum SidebarBodyComponentId {
AddContent = 'add-content',
Expand All @@ -18,8 +17,8 @@ export interface LibraryContextData {
closeLibrarySidebar: () => void;
openAddContentSidebar: () => void;
openInfoSidebar: () => void;
openComponentInfoSidebar: (componentHit: ContentHit) => void;
currentComponentData?: ContentHit;
openComponentInfoSidebar: (usageKey: string) => void;
currentComponentUsageKey?: string;
isCreateCollectionModalOpen: boolean;
openCreateCollectionModal: () => void;
closeCreateCollectionModal: () => void;
Expand Down Expand Up @@ -48,14 +47,14 @@ const LibraryContext = React.createContext<LibraryContextData | undefined>(undef
*/
export const LibraryProvider = (props: { children?: React.ReactNode, libraryId: string }) => {
const [sidebarBodyComponent, setSidebarBodyComponent] = React.useState<SidebarBodyComponentId | null>(null);
const [currentComponentData, setCurrentComponentData] = React.useState<ContentHit>();
const [currentComponentUsageKey, setCurrentComponentUsageKey] = React.useState<string>();
const [currentCollectionId, setcurrentCollectionId] = React.useState<string>();
const [isCreateCollectionModalOpen, openCreateCollectionModal, closeCreateCollectionModal] = useToggle(false);
const [componentBeingEdited, openComponentEditor] = React.useState<string | undefined>();
const closeComponentEditor = React.useCallback(() => openComponentEditor(undefined), []);

const resetSidebar = React.useCallback(() => {
setCurrentComponentData(undefined);
setCurrentComponentUsageKey(undefined);
setcurrentCollectionId(undefined);
setSidebarBodyComponent(null);
}, []);
Expand All @@ -72,9 +71,9 @@ export const LibraryProvider = (props: { children?: React.ReactNode, libraryId:
setSidebarBodyComponent(SidebarBodyComponentId.Info);
}, []);
const openComponentInfoSidebar = React.useCallback(
(componentHit: ContentHit) => {
(usageKey: string) => {
resetSidebar();
setCurrentComponentData(componentHit);
setCurrentComponentUsageKey(usageKey);
setSidebarBodyComponent(SidebarBodyComponentId.ComponentInfo);
},
[],
Expand All @@ -92,7 +91,7 @@ export const LibraryProvider = (props: { children?: React.ReactNode, libraryId:
openAddContentSidebar,
openInfoSidebar,
openComponentInfoSidebar,
currentComponentData,
currentComponentUsageKey,
isCreateCollectionModalOpen,
openCreateCollectionModal,
closeCreateCollectionModal,
Expand All @@ -108,7 +107,7 @@ export const LibraryProvider = (props: { children?: React.ReactNode, libraryId:
openAddContentSidebar,
openInfoSidebar,
openComponentInfoSidebar,
currentComponentData,
currentComponentUsageKey,
isCreateCollectionModalOpen,
openCreateCollectionModal,
closeCreateCollectionModal,
Expand Down
8 changes: 3 additions & 5 deletions src/library-authoring/component-info/ComponentInfo.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,18 +14,16 @@ import messages from './messages';
import { canEditComponent } from '../components/ComponentEditorModal';
import { useLibraryContext } from '../common/context';
import { useContentLibrary } from '../data/apiHooks';
import { ContentHit } from '../../search-manager';

interface ComponentInfoProps {
contentHit: ContentHit;
usageKey: string;
}

const ComponentInfo = ({ contentHit }: ComponentInfoProps) => {
const ComponentInfo = ({ usageKey }: ComponentInfoProps) => {
const intl = useIntl();
const { libraryId, openComponentEditor } = useLibraryContext();
const { data: libraryData } = useContentLibrary(libraryId);
const canEdit = libraryData?.canEditLibrary && canEditComponent(usageKey);
const { usageKey } = contentHit;

return (
<Stack>
Expand All @@ -51,7 +49,7 @@ const ComponentInfo = ({ contentHit }: ComponentInfoProps) => {
<ComponentPreview usageKey={usageKey} />
</Tab>
<Tab eventKey="manage" title={intl.formatMessage(messages.manageTabTitle)}>
<ComponentManagement contentHit={contentHit} />
<ComponentManagement usageKey={usageKey} />
</Tab>
<Tab eventKey="details" title={intl.formatMessage(messages.detailsTabTitle)}>
<ComponentDetails usageKey={usageKey} />
Expand Down
14 changes: 9 additions & 5 deletions src/library-authoring/component-info/ComponentManagement.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,18 +10,22 @@ import messages from './messages';
import { ContentTagsDrawer } from '../../content-tags-drawer';
import { useContentTaxonomyTagsData } from '../../content-tags-drawer/data/apiHooks';
import ManageCollections from './ManageCollections';
import { ContentHit } from '../../search-manager';
import { ContentHit, useGetDocumentByUsageKey } from '../../search-manager';

interface ComponentManagementProps {
contentHit: ContentHit;
usageKey: string;
}

const ComponentManagement = ({ contentHit }: ComponentManagementProps) => {
const ComponentManagement = ({ usageKey }: ComponentManagementProps) => {
const intl = useIntl();
const { usageKey } = contentHit;
const { data: componentMetadata } = useLibraryBlockMetadata(usageKey);
const { data: componentTags } = useContentTaxonomyTagsData(usageKey);
const { data: contentHit } = useGetDocumentByUsageKey(usageKey) as { data: ContentHit };

const collectionsCount = React.useMemo(
() => contentHit?.collections?.displayName?.length || 0,
[contentHit]

Check failure on line 27 in src/library-authoring/component-info/ComponentManagement.tsx

View workflow job for this annotation

GitHub Actions / tests (20)

Missing trailing comma
);
const tagsCount = React.useMemo(() => {
if (!componentTags) {
return 0;
Expand Down Expand Up @@ -74,7 +78,7 @@ const ComponentManagement = ({ contentHit }: ComponentManagementProps) => {
title={(
<Stack gap={1} direction="horizontal">
<Icon src={BookOpen} />
{intl.formatMessage(messages.manageTabCollectionsTitle)}
{intl.formatMessage(messages.manageTabCollectionsTitle, { count: collectionsCount })}
</Stack>
)}
className="border-0"
Expand Down
14 changes: 2 additions & 12 deletions src/library-authoring/component-info/ManageCollections.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,12 +11,10 @@ import {
SearchKeywordsField,
SearchSortWidget,
useSearchContext,
useGetDocumentByBlockId,
} from '../../search-manager';
import messages from './messages';
import { useUpdateComponentCollections } from '../data/apiHooks';
import { ToastContext } from '../../generic/toast-context';
import Loading from '../../generic/Loading';

interface ManageCollectionsProps {
contentHit: ContentHit;
Expand Down Expand Up @@ -187,28 +185,20 @@ const ComponentCollections = ({ collections, onManageClick }: {
};

const ManageCollections = ({ contentHit }: ManageCollectionsProps) => {
const { data, isLoading } = useGetDocumentByBlockId(
contentHit.contextKey,
contentHit.blockId,
) as { data: ContentHit, isLoading: boolean };
const [editing, setEditing] = useState(false);

if (isLoading) {
return <Loading />;
}

if (editing) {
return (
<AddToCollectionsDrawer
contentHit={data}
contentHit={contentHit}
onClose={() => setEditing(false)}
key={contentHit.usageKey}
/>
);
}
return (
<ComponentCollections
collections={data.collections?.displayName}
collections={contentHit.collections?.displayName}
onManageClick={() => setEditing(true)}
/>
);
Expand Down
2 changes: 1 addition & 1 deletion src/library-authoring/component-info/messages.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ const messages = defineMessages({
},
manageTabCollectionsTitle: {
id: 'course-authoring.library-authoring.component.manage-tab.collections-title',
defaultMessage: 'Collections',
defaultMessage: 'Collections ({count})',
description: 'Title for the Collections container in the management tab',
},
detailsTabTitle: {
Expand Down
2 changes: 1 addition & 1 deletion src/library-authoring/components/ComponentCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ const ComponentCard = ({ contentHit } : ComponentCardProps) => {
<ComponentMenu usageKey={usageKey} />
</ActionRow>
)}
openInfoSidebar={() => openComponentInfoSidebar(contentHit)}
openInfoSidebar={() => openComponentInfoSidebar(usageKey)}
/>
);
};
Expand Down
8 changes: 4 additions & 4 deletions src/library-authoring/data/apiHooks.ts
Original file line number Diff line number Diff line change
Expand Up @@ -325,13 +325,13 @@ export const useUpdateComponentCollections = (libraryId: string, usageKey: strin
queryClient.invalidateQueries({ predicate: (query) => libraryQueryPredicate(query, libraryId) });
queryClient.invalidateQueries({
predicate: (query) => {
const queryLibId = query.queryKey[5];
const queryUsageKey = query.queryKey[5];
if (
(query.queryKey[0] !== 'content_search' && query.queryKey[1] !== 'get_by_block_id')
|| typeof queryLibId !== 'string') {
(query.queryKey[0] !== 'content_search' && query.queryKey[1] !== 'get_by_usage_key')
|| typeof queryUsageKey !== 'string') {
return false;
}
return queryLibId === libraryId;
return queryUsageKey === usageKey;
},
});
},
Expand Down
6 changes: 3 additions & 3 deletions src/library-authoring/library-sidebar/LibrarySidebar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -33,15 +33,15 @@ const LibrarySidebar = ({ library }: LibrarySidebarProps) => {
const {
sidebarBodyComponent,
closeLibrarySidebar,
currentComponentData,
currentComponentUsageKey,
currentCollectionId,
} = useLibraryContext();

const bodyComponentMap = {
[SidebarBodyComponentId.AddContent]: <AddContentContainer />,
[SidebarBodyComponentId.Info]: <LibraryInfo library={library} />,
[SidebarBodyComponentId.ComponentInfo]: (
currentComponentData && <ComponentInfo contentHit={currentComponentData} />
currentComponentUsageKey && <ComponentInfo usageKey={currentComponentUsageKey} />
),
[SidebarBodyComponentId.CollectionInfo]: (
currentCollectionId && <CollectionInfo library={library} collectionId={currentCollectionId} />
Expand All @@ -53,7 +53,7 @@ const LibrarySidebar = ({ library }: LibrarySidebarProps) => {
[SidebarBodyComponentId.AddContent]: <AddContentHeader />,
[SidebarBodyComponentId.Info]: <LibraryInfoHeader library={library} />,
[SidebarBodyComponentId.ComponentInfo]: (
currentComponentData && <ComponentInfoHeader library={library} usageKey={currentComponentData.usageKey} />
currentComponentUsageKey && <ComponentInfoHeader library={library} usageKey={currentComponentUsageKey} />
),
[SidebarBodyComponentId.CollectionInfo]: (
currentCollectionId && <CollectionInfoHeader library={library} collectionId={currentCollectionId} />
Expand Down
10 changes: 4 additions & 6 deletions src/search-manager/data/api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -558,20 +558,18 @@ export async function fetchDocumentById({ client, indexName, id } : {
}

/**
* Fetch a content hit by block Id and library key i.e. context_key
* Fetch a content hit by usage key
*/
export const fetchContentByBlockId = async (
export const fetchContentByUsageKey = async (
client: MeiliSearch,
indexName: string,
libraryKey: string,
blockId: string,
usageKey: string,
): Promise<CollectionHit | ContentHit> => {
const { results } = await client.multiSearch({
queries: [{
indexUid: indexName,
filter: [
`context_key = "${libraryKey}"`,
`block_id = "${blockId}"`,
`usage_key = "${usageKey}"`,
],
limit: 1,
}],
Expand Down
11 changes: 5 additions & 6 deletions src/search-manager/data/apiHooks.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import {
fetchDocumentById,
fetchBlockTypes,
OverrideQueries,
fetchContentByBlockId,
fetchContentByUsageKey,
} from './api';

/**
Expand Down Expand Up @@ -286,19 +286,18 @@ export const useGetSingleDocument = ({ client, indexName, id }: {
);

/* istanbul ignore next */
export const useGetDocumentByBlockId = (libraryKey: string, blockId: string) => {
export const useGetDocumentByUsageKey = (usageKey: string) => {
const { client, indexName } = useContentSearchConnection();
return useQuery({
enabled: client !== undefined && indexName !== undefined,
queryKey: [
'content_search',
'get_by_block_id',
'get_by_usage_key',
client?.config.apiKey,
client?.config.host,
indexName,
libraryKey,
blockId,
usageKey,
],
queryFn: () => fetchContentByBlockId(client!, indexName!, libraryKey, blockId),
queryFn: () => fetchContentByUsageKey(client!, indexName!, usageKey),
});
};
2 changes: 1 addition & 1 deletion src/search-manager/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,6 @@ export { default as SearchSortWidget } from './SearchSortWidget';
export { default as Stats } from './Stats';
export { HIGHLIGHT_PRE_TAG, HIGHLIGHT_POST_TAG } from './data/api';
export { useGetBlockTypes } from './data/apiHooks';
export { useGetDocumentByBlockId } from './data/apiHooks';
export { useGetDocumentByUsageKey } from './data/apiHooks';

export type { CollectionHit, ContentHit, ContentHitTags } from './data/api';

0 comments on commit a57cf0e

Please sign in to comment.