From e26ed0b6f0513552584ea52e293269e7a73dd048 Mon Sep 17 00:00:00 2001 From: Hongbo Wu Date: Fri, 17 Nov 2023 18:26:00 +0800 Subject: [PATCH] add RSS label to the following feed items --- packages/api/src/repository/label.ts | 5 ++- packages/api/src/routers/svc/following.ts | 34 +++++++++++++++++-- packages/api/src/services/labels.ts | 14 ++++++-- packages/api/src/services/library_item.ts | 32 ++++++++--------- packages/api/src/services/save_page.ts | 2 ++ packages/api/test/resolvers/article.test.ts | 15 ++++++-- .../templates/homeFeed/LibraryFilterMenu.tsx | 4 +-- 7 files changed, 79 insertions(+), 27 deletions(-) diff --git a/packages/api/src/repository/label.ts b/packages/api/src/repository/label.ts index d21708961..093a34bd9 100644 --- a/packages/api/src/repository/label.ts +++ b/packages/api/src/repository/label.ts @@ -32,7 +32,10 @@ const convertToLabel = (label: CreateLabelInput, userId: string) => { return { user: { id: userId }, name: label.name, - color: label.color || generateRandomColor(), // assign a random color if not provided + color: + label.color || + getInternalLabelWithColor(label.name)?.color || + generateRandomColor(), // assign a random color if not provided description: label.description, internal: isLabelInternal(label.name), } diff --git a/packages/api/src/routers/svc/following.ts b/packages/api/src/routers/svc/following.ts index 68a016c60..1bbbdab6d 100644 --- a/packages/api/src/routers/svc/following.ts +++ b/packages/api/src/routers/svc/following.ts @@ -1,5 +1,9 @@ /* eslint-disable @typescript-eslint/no-misused-promises */ import express from 'express' +import { + findOrCreateLabels, + saveLabelsInLibraryItem, +} from '../../services/labels' import { saveFeedItemInFollowing } from '../../services/library_item' import { logger } from '../../utils/logger' @@ -49,16 +53,40 @@ export function followingServiceRouter() { return res.status(400).send('INVALID_REQUEST_BODY') } - if (req.body.addedToFollowingFrom === 'feed') { - logger.info('saving feed item') + if ( + req.body.addedToFollowingFrom === 'feed' && + req.body.userIds.length > 0 + ) { + const userId = req.body.userIds[0] + logger.info('saving feed item', userId) - const result = await saveFeedItemInFollowing(req.body) + const result = await saveFeedItemInFollowing(req.body, userId) if (result.identifiers.length === 0) { logger.error('error saving feed item in following') return res.status(500).send('ERROR_SAVING_FEED_ITEM') } logger.info('feed item saved in following') + + // add RSS label to the item + const labels = await findOrCreateLabels( + [ + { + name: 'RSS', + }, + ], + userId + ) + await saveLabelsInLibraryItem( + labels, + result.identifiers[0].id, + userId, + undefined, + true + ) + + logger.info('RSS label added to the item') + return res.sendStatus(200) } diff --git a/packages/api/src/services/labels.ts b/packages/api/src/services/labels.ts index a33e1e2e6..a015098be 100644 --- a/packages/api/src/services/labels.ts +++ b/packages/api/src/services/labels.ts @@ -69,7 +69,8 @@ export const saveLabelsInLibraryItem = async ( labels: Label[], libraryItemId: string, userId: string, - pubsub = createPubSubClient() + pubsub = createPubSubClient(), + skipPubSub = false ) => { await authTrx( async (tx) => { @@ -92,6 +93,10 @@ export const saveLabelsInLibraryItem = async ( userId ) + if (skipPubSub) { + return + } + // create pubsub event await pubsub.entityCreated( EntityType.LABEL, @@ -104,7 +109,8 @@ export const addLabelsToLibraryItem = async ( labels: Label[], libraryItemId: string, userId: string, - pubsub = createPubSubClient() + pubsub = createPubSubClient(), + skipPubSub = false ) => { await authTrx( async (tx) => { @@ -128,6 +134,10 @@ export const addLabelsToLibraryItem = async ( userId ) + if (skipPubSub) { + return + } + // create pubsub event await pubsub.entityCreated( EntityType.LABEL, diff --git a/packages/api/src/services/library_item.ts b/packages/api/src/services/library_item.ts index 9b6f9b4e1..acb84fa6e 100644 --- a/packages/api/src/services/library_item.ts +++ b/packages/api/src/services/library_item.ts @@ -9,7 +9,6 @@ import { createPubSubClient, EntityType } from '../pubsub' import { authTrx, getColumns } from '../repository' import { libraryItemRepository } from '../repository/library_item' import { SaveFollowingItemRequest } from '../routers/svc/following' -import { SetClaimsRole } from '../utils/dictionary' import { generateSlug, wordsCount } from '../utils/helpers' import { DateFilter, @@ -248,7 +247,7 @@ const buildWhereClause = ( if (args.noFilters) { args.noFilters.forEach((filter) => { queryBuilder.andWhere( - `library_item.${filter.field} = '{}' OR library_item.${filter.field} IS NULL` + `(library_item.${filter.field} = '{}' OR library_item.${filter.field} IS NULL)` ) }) } @@ -397,7 +396,6 @@ export const updateLibraryItem = async ( const updatedLibraryItem = await authTrx( async (tx) => { const itemRepo = tx.withRepository(libraryItemRepository) - await itemRepo.update(id, libraryItem) // reset deletedAt and archivedAt switch (libraryItem.state) { @@ -413,6 +411,7 @@ export const updateLibraryItem = async ( libraryItem.deletedAt = null break } + await itemRepo.update(id, libraryItem) return itemRepo.findOneByOrFail({ id }) }, @@ -551,31 +550,32 @@ export const createLibraryItem = async ( return newLibraryItem } -export const saveFeedItemInFollowing = (input: SaveFollowingItemRequest) => { +export const saveFeedItemInFollowing = ( + input: SaveFollowingItemRequest, + userId: string +) => { return authTrx( async (tx) => { - const libraryItems: QueryDeepPartialEntity[] = - input.userIds.map((userId) => ({ - ...input, - user: { id: userId }, - originalUrl: input.url, - subscription: input.addedToFollowingBy, - folder: InFilter.FOLLOWING, - slug: generateSlug(input.title), - })) + const itemToSave: QueryDeepPartialEntity = { + ...input, + user: { id: userId }, + originalUrl: input.url, + subscription: input.addedToFollowingBy, + folder: InFilter.FOLLOWING, + slug: generateSlug(input.title), + } return tx .getRepository(LibraryItem) .createQueryBuilder() .insert() - .values(libraryItems) + .values(itemToSave) .orIgnore() // ignore if the item already exists .returning('*') .execute() }, undefined, - undefined, - SetClaimsRole.ADMIN + userId ) } diff --git a/packages/api/src/services/save_page.ts b/packages/api/src/services/save_page.ts index 14347bde8..6eb5ebff3 100644 --- a/packages/api/src/services/save_page.ts +++ b/packages/api/src/services/save_page.ts @@ -273,5 +273,7 @@ export const parsedContentToLibraryItem = ({ contentReader: contentReaderForLibraryItem(itemType, uploadFileId), subscription: rssFeedUrl, folder: 'inbox', + archivedAt: + state === ArticleSavingRequestStatus.Archived ? new Date() : null, } } diff --git a/packages/api/test/resolvers/article.test.ts b/packages/api/test/resolvers/article.test.ts index 6227f2cd9..e5fb2d5ee 100644 --- a/packages/api/test/resolvers/article.test.ts +++ b/packages/api/test/resolvers/article.test.ts @@ -692,7 +692,7 @@ describe('Article API', () => { 200 ) const item = await findLibraryItemById(itemId, user.id) - expect(item?.folder).to.eql('trash') + expect(item?.state).to.eql(LibraryItemState.Deleted) }) }) @@ -1153,12 +1153,12 @@ describe('Article API', () => { }) }) - context("when in:inbox label:test' is in the query", () => { + context('when in:inbox no:subscription label:test is in the query', () => { let items: LibraryItem[] = [] let label: Label before(async () => { - keyword = 'in:inbox label:test' + keyword = 'in:inbox no:subscription label:test' // Create some test items label = await createLabel('test', '', user.id) items = await createLibraryItems( @@ -1170,6 +1170,14 @@ describe('Article API', () => { slug: 'test slug 1', originalUrl: `${url}/test1`, }, + { + user, + title: 'test title 2', + readableContent: '

test 2

', + slug: 'test slug 2', + originalUrl: `${url}/test2`, + subscription: 'test subscription', + }, { user, title: 'test title 3', @@ -1184,6 +1192,7 @@ describe('Article API', () => { ) await saveLabelsInLibraryItem([label], items[0].id, user.id) await saveLabelsInLibraryItem([label], items[1].id, user.id) + await saveLabelsInLibraryItem([label], items[2].id, user.id) }) after(async () => { diff --git a/packages/web/components/templates/homeFeed/LibraryFilterMenu.tsx b/packages/web/components/templates/homeFeed/LibraryFilterMenu.tsx index 2149ed68b..0c9000ea2 100644 --- a/packages/web/components/templates/homeFeed/LibraryFilterMenu.tsx +++ b/packages/web/components/templates/homeFeed/LibraryFilterMenu.tsx @@ -242,9 +242,9 @@ function Subscriptions( {!collapsed ? ( <> - +