diff --git a/packages/api/src/generated/graphql.ts b/packages/api/src/generated/graphql.ts index cd4b67b31..a632e26a8 100644 --- a/packages/api/src/generated/graphql.ts +++ b/packages/api/src/generated/graphql.ts @@ -2748,6 +2748,7 @@ export type SearchItem = { directionality?: Maybe; feedContent?: Maybe; folder: Scalars['String']; + format?: Maybe; highlights?: Maybe>; id: Scalars['ID']; image?: Maybe; @@ -6617,6 +6618,7 @@ export type SearchItemResolvers, ParentType, ContextType>; feedContent?: Resolver, ParentType, ContextType>; folder?: Resolver; + format?: Resolver, ParentType, ContextType>; highlights?: Resolver>, ParentType, ContextType>; id?: Resolver; image?: Resolver, ParentType, ContextType>; diff --git a/packages/api/src/generated/schema.graphql b/packages/api/src/generated/schema.graphql index e48fe3cff..815fc9502 100644 --- a/packages/api/src/generated/schema.graphql +++ b/packages/api/src/generated/schema.graphql @@ -2102,6 +2102,7 @@ type SearchItem { directionality: DirectionalityType feedContent: String folder: String! + format: String highlights: [Highlight!] id: ID! image: String diff --git a/packages/api/src/resolvers/article/index.ts b/packages/api/src/resolvers/article/index.ts index a5c80caa8..942bae7be 100644 --- a/packages/api/src/resolvers/article/index.ts +++ b/packages/api/src/resolvers/article/index.ts @@ -88,6 +88,7 @@ import { setFileUploadComplete, } from '../../services/upload_file' import { traceAs } from '../../tracing' +import { Merge } from '../../util' import { analytics } from '../../utils/analytics' import { isSiteBlockedForParse } from '../../utils/blocked' import { enqueueBulkAction } from '../../utils/createTask' @@ -697,39 +698,9 @@ export const searchResolver = authorized< libraryItems.pop() } - // const edges = await Promise.all( - // libraryItems.map(async (libraryItem) => { - // libraryItem.highlights = await findHighlightsByLibraryItemId( - // libraryItem.id, - // uid - // ) - - // if (params.includeContent && libraryItem.readableContent) { - // // convert html to the requested format - // const format = params.format || ArticleFormat.Html - // try { - // const converter = contentConverter(format) - // if (converter) { - // libraryItem.readableContent = converter( - // libraryItem.readableContent, - // libraryItem.highlights - // ) - // } - // } catch (error) { - // log.error('Error converting content', error) - // } - // } - - // return { - // node: libraryItemToSearchItem(libraryItem), - // cursor: endCursor, - // } - // }) - // ) - return { edges: libraryItems.map((item) => ({ - node: libraryItemToSearchItem(item), + node: libraryItemToSearchItem(item, params.format as ArticleFormat), cursor: endCursor, })), pageInfo: { diff --git a/packages/api/src/resolvers/function_resolvers.ts b/packages/api/src/resolvers/function_resolvers.ts index e6b997332..30cae9cc3 100644 --- a/packages/api/src/resolvers/function_resolvers.ts +++ b/packages/api/src/resolvers/function_resolvers.ts @@ -4,6 +4,7 @@ /* eslint-disable @typescript-eslint/no-unsafe-member-access */ /* eslint-disable @typescript-eslint/explicit-module-boundary-types */ import { createHmac } from 'crypto' +import { Highlight as HighlightEntity } from '../entity/highlight' import { EXISTING_NEWSLETTER_FOLDER, NewsletterEmail, @@ -34,11 +35,16 @@ import { wordsCount, } from '../utils/helpers' import { createImageProxyUrl } from '../utils/imageproxy' +import { contentConverter } from '../utils/parser' import { generateDownloadSignedUrl, generateUploadFilePathName, } from '../utils/uploads' -import { emptyTrashResolver, fetchContentResolver } from './article' +import { + ArticleFormat, + emptyTrashResolver, + fetchContentResolver, +} from './article' import { addDiscoverFeedResolver, deleteDiscoverArticleResolver, @@ -568,6 +574,42 @@ export const functionResolvers = { return [] }, ...readingProgressHandlers, + async content( + item: { + id: string + content?: string + highlightAnnotations?: string[] + format?: ArticleFormat + }, + _: unknown, + ctx: WithDataSourcesContext + ) { + // convert html to the requested format if requested + if (item.format && item.content) { + let highlights: HighlightEntity[] = [] + // load highlights if needed + if ( + item.format === 'highlightedMarkdown' && + item.highlightAnnotations?.length + ) { + highlights = await ctx.dataLoaders.highlights.load(item.id) + } + + try { + ctx.log.info(`Converting content to: ${item.format}`) + + // convert html to the requested format + const converter = contentConverter(item.format) + if (converter) { + return converter(item.content, highlights) + } + } catch (error) { + ctx.log.error('Error converting content', error) + } + } + + return item.content + }, }, Subscription: { newsletterEmail(subscription: Subscription) { diff --git a/packages/api/src/schema.ts b/packages/api/src/schema.ts index acae6f520..8d112d509 100755 --- a/packages/api/src/schema.ts +++ b/packages/api/src/schema.ts @@ -1657,6 +1657,7 @@ const schema = gql` folder: String! aiSummary: String directionality: DirectionalityType + format: String } type SearchItemEdge { diff --git a/packages/api/src/utils/helpers.ts b/packages/api/src/utils/helpers.ts index 785e5d5ef..85abc5467 100644 --- a/packages/api/src/utils/helpers.ts +++ b/packages/api/src/utils/helpers.ts @@ -26,6 +26,7 @@ import { SearchItem, } from '../generated/graphql' import { createPubSubClient } from '../pubsub' +import { ArticleFormat } from '../resolvers' import { validateUrl } from '../services/create_page_save_request' import { updateLibraryItem } from '../services/library_item' import { Merge } from '../util' @@ -230,7 +231,10 @@ export const libraryItemToArticle = (item: LibraryItem): Article => ({ directionality: item.directionality as unknown as DirectionalityType, }) -export const libraryItemToSearchItem = (item: LibraryItem): SearchItem => ({ +export const libraryItemToSearchItem = ( + item: LibraryItem, + format?: ArticleFormat +): SearchItem => ({ ...item, url: item.originalUrl, state: item.state as unknown as ArticleSavingRequestStatus, @@ -247,6 +251,7 @@ export const libraryItemToSearchItem = (item: LibraryItem): SearchItem => ({ highlights: item.highlights?.map(highlightDataToHighlight), wordsCount: item.wordCount, directionality: item.directionality as unknown as DirectionalityType, + format, }) export const isParsingTimeout = (libraryItem: LibraryItem): boolean => { diff --git a/packages/api/src/utils/parser.ts b/packages/api/src/utils/parser.ts index 3122a72bd..e76a8ed15 100644 --- a/packages/api/src/utils/parser.ts +++ b/packages/api/src/utils/parser.ts @@ -647,7 +647,6 @@ export const contentConverter = ( return htmlToMarkdown case ArticleFormat.HighlightedMarkdown: return htmlToHighlightedMarkdown - case ArticleFormat.Html: default: return undefined }