From d0641084f9ae05bc0475454f5f38fcdc3b2e3b41 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?J=C3=A9r=C3=A9my=20M?= Date: Fri, 28 Jul 2023 08:22:16 +0200 Subject: [PATCH] feat: rename comment thread into activity (#939) * feat: rename commentThread into activity server * feat: rename commentThread into activity front * feat: migration only create tables feat: migration only create tables * Update activities * fix: rebase partial fix * fix: all rebase problems and drop activity target alter * fix: lint * Update migration * Update migration * Fix conflicts * Fix conflicts --------- Co-authored-by: Charles Bochet --- front/src/generated/graphql.tsx | 1123 +++++++++-------- .../comment/__stories__/Comment.stories.tsx | 4 +- .../__stories__/CommentHeader.stories.tsx | 4 +- ...dBodyEditor.tsx => ActivityBodyEditor.tsx} | 35 +- ...hreadComments.tsx => ActivityComments.tsx} | 16 +- ...ateButton.tsx => ActivityCreateButton.tsx} | 6 +- ...entThreadEditor.tsx => ActivityEditor.tsx} | 90 +- ...nPicker.tsx => ActivityRelationPicker.tsx} | 29 +- ...mmentThreadTitle.tsx => ActivityTitle.tsx} | 2 +- ...eDropdown.tsx => ActivityTypeDropdown.tsx} | 8 +- ...tsx => ActivityRelationPicker.stories.tsx} | 14 +- .../useHandleCheckableActivityTargetChange.ts | 84 ++ ...andleCheckableCommentThreadTargetChange.ts | 84 -- ...rawer.ts => useOpenActivityRightDrawer.ts} | 14 +- ...awer.ts => useOpenCreateActivityDrawer.ts} | 33 +- ...nCreateActivityDrawerForSelectedRowIds.ts} | 28 +- .../src/modules/activities/queries/create.ts | 26 +- .../src/modules/activities/queries/select.ts | 28 +- .../src/modules/activities/queries/update.ts | 50 +- .../right-drawer/components/Activity.tsx | 201 +++ ...eadActionBar.tsx => ActivityActionBar.tsx} | 18 +- .../right-drawer/components/CommentThread.tsx | 34 - ...read.tsx => RightDrawerCreateActivity.tsx} | 14 +- ...Thread.tsx => RightDrawerEditActivity.tsx} | 10 +- .../states/commentableEntityArrayState.ts | 2 +- .../states/viewableActivityIdState.ts | 6 + .../states/viewableCommentThreadIdState.ts | 6 - .../timeline/components/Timeline.tsx | 30 +- .../timeline/components/TimelineActivity.tsx | 57 +- .../activities/types/ActivityForDrawer.ts | 4 + .../activities/types/CommentForDrawer.ts | 6 +- .../types/CommentThreadForDrawer.ts | 4 - .../modules/apollo/hooks/useApolloFactory.ts | 10 +- .../components/CompanyEditableNameCell.tsx | 2 +- front/src/modules/companies/queries/select.ts | 2 +- front/src/modules/companies/queries/show.ts | 2 +- .../components/EditableCompanyNameCell.tsx | 2 +- ...leActionBarButtonCreateActivityCompany.tsx | 14 + ...ionBarButtonCreateCommentThreadCompany.tsx | 14 - .../table/components/companies-mock-data.ts | 12 +- .../table/hooks/useSetCompanyEntityTable.ts | 4 +- .../components/EditablePeopleFullName.tsx | 6 +- .../people/hooks/useSetPeopleEntityTable.ts | 4 +- front/src/modules/people/queries/select.ts | 6 +- front/src/modules/people/queries/show.ts | 2 +- .../components/EditablePeopleFullNameCell.tsx | 2 +- ...bleActionBarButtonCreateActivityPeople.tsx | 14 + ...tionBarButtonCreateCommentThreadPeople.tsx | 14 - .../ui/button/components/DropdownButton.tsx | 144 +++ .../components/RightDrawerRouter.tsx | 12 +- .../ui/right-drawer/types/RightDrawerPages.ts | 4 +- .../editable-cell/types/EditableChip.tsx | 2 +- front/src/pages/companies/Companies.tsx | 4 +- .../src/pages/companies/CompaniesMockMode.tsx | 4 +- .../companies/__stories__/Company.stories.tsx | 34 +- front/src/pages/people/People.tsx | 4 +- .../{comment-threads.ts => activities.ts} | 52 +- front/src/testing/mock-data/companies.ts | 16 +- front/src/testing/mock-data/people.ts | 10 +- server/src/ability/ability.factory.ts | 26 +- server/src/ability/ability.module.ts | 72 +- .../activity-target.ability-handler.ts | 79 ++ .../handlers/activity.ability-handler.ts | 73 ++ .../handlers/attachment.ability-handler.ts | 8 +- .../comment-thread-target.ability-handler.ts | 118 -- .../comment-thread.ability-handler.ts | 110 -- server/src/core/activity/activity.module.ts | 11 + .../resolvers/activity.resolver.spec.ts} | 14 +- .../activity/resolvers/activity.resolver.ts | 156 +++ .../services/activity-target.service.spec.ts} | 12 +- .../services/activity-target.service.ts | 40 + .../services/activity.service.spec.ts} | 10 +- .../activity/services/activity.service.ts | 39 + server/src/core/comment/comment.module.ts | 17 +- .../{resolvers => }/comment.resolver.spec.ts | 2 +- .../{resolvers => }/comment.resolver.ts | 2 +- .../{services => }/comment.service.spec.ts | 0 .../comment/{services => }/comment.service.ts | 0 .../resolvers/comment-thread.resolver.ts | 150 --- .../services/comment-thread-target.service.ts | 41 - .../services/comment-thread.service.ts | 39 - .../company-relations.resolver.spec.ts | 6 +- .../company/company-relations.resolver.ts | 38 +- server/src/core/company/company.module.ts | 3 +- server/src/core/core.module.ts | 2 + .../person/person-relations.resolver.spec.ts | 6 +- .../core/person/person-relations.resolver.ts | 38 +- server/src/core/person/person.module.ts | 3 +- server/src/core/person/person.resolver.ts | 2 +- .../workspace/services/workspace.service.ts | 14 +- .../migration.sql | 1 - .../migration.sql | 69 + server/src/database/schema.prisma | 138 +- server/src/database/seeds/comments.ts | 28 +- .../utils/prisma-select/model-select-map.ts | 4 +- 95 files changed, 2112 insertions(+), 1725 deletions(-) rename front/src/modules/activities/components/{CommentThreadBodyEditor.tsx => ActivityBodyEditor.tsx} (55%) rename front/src/modules/activities/components/{CommentThreadComments.tsx => ActivityComments.tsx} (84%) rename front/src/modules/activities/components/{CommentThreadCreateButton.tsx => ActivityCreateButton.tsx} (88%) rename front/src/modules/activities/components/{CommentThreadEditor.tsx => ActivityEditor.tsx} (61%) rename front/src/modules/activities/components/{CommentThreadRelationPicker.tsx => ActivityRelationPicker.tsx} (90%) rename front/src/modules/activities/components/{CommentThreadTitle.tsx => ActivityTitle.tsx} (98%) rename front/src/modules/activities/components/{CommentThreadTypeDropdown.tsx => ActivityTypeDropdown.tsx} (67%) rename front/src/modules/activities/components/__stories__/{CommentThreadRelationPicker.stories.tsx => ActivityRelationPicker.stories.tsx} (59%) create mode 100644 front/src/modules/activities/hooks/useHandleCheckableActivityTargetChange.ts delete mode 100644 front/src/modules/activities/hooks/useHandleCheckableCommentThreadTargetChange.ts rename front/src/modules/activities/hooks/{useOpenCommentThreadRightDrawer.ts => useOpenActivityRightDrawer.ts} (56%) rename front/src/modules/activities/hooks/{useOpenCreateCommentThreadDrawer.ts => useOpenCreateActivityDrawer.ts} (65%) rename front/src/modules/activities/hooks/{useOpenCreateCommentDrawerForSelectedRowIds.ts => useOpenCreateActivityDrawerForSelectedRowIds.ts} (71%) create mode 100644 front/src/modules/activities/right-drawer/components/Activity.tsx rename front/src/modules/activities/right-drawer/components/{CommentThreadActionBar.tsx => ActivityActionBar.tsx} (70%) delete mode 100644 front/src/modules/activities/right-drawer/components/CommentThread.tsx rename front/src/modules/activities/right-drawer/components/create/{RightDrawerCreateCommentThread.tsx => RightDrawerCreateActivity.tsx} (58%) rename front/src/modules/activities/right-drawer/components/edit/{RightDrawerEditCommentThread.tsx => RightDrawerEditActivity.tsx} (55%) create mode 100644 front/src/modules/activities/states/viewableActivityIdState.ts delete mode 100644 front/src/modules/activities/states/viewableCommentThreadIdState.ts create mode 100644 front/src/modules/activities/types/ActivityForDrawer.ts delete mode 100644 front/src/modules/activities/types/CommentThreadForDrawer.ts create mode 100644 front/src/modules/companies/table/components/TableActionBarButtonCreateActivityCompany.tsx delete mode 100644 front/src/modules/companies/table/components/TableActionBarButtonCreateCommentThreadCompany.tsx create mode 100644 front/src/modules/people/table/components/TableActionBarButtonCreateActivityPeople.tsx delete mode 100644 front/src/modules/people/table/components/TableActionBarButtonCreateCommentThreadPeople.tsx create mode 100644 front/src/modules/ui/button/components/DropdownButton.tsx rename front/src/testing/mock-data/{comment-threads.ts => activities.ts} (77%) create mode 100644 server/src/ability/handlers/activity-target.ability-handler.ts create mode 100644 server/src/ability/handlers/activity.ability-handler.ts delete mode 100644 server/src/ability/handlers/comment-thread-target.ability-handler.ts delete mode 100644 server/src/ability/handlers/comment-thread.ability-handler.ts create mode 100644 server/src/core/activity/activity.module.ts rename server/src/core/{comment/resolvers/comment-thread.resolver.spec.ts => activity/resolvers/activity.resolver.spec.ts} (55%) create mode 100644 server/src/core/activity/resolvers/activity.resolver.ts rename server/src/core/{comment/services/comment-thread-target.service.spec.ts => activity/services/activity-target.service.spec.ts} (63%) create mode 100644 server/src/core/activity/services/activity-target.service.ts rename server/src/core/{comment/services/comment-thread.service.spec.ts => activity/services/activity.service.spec.ts} (67%) create mode 100644 server/src/core/activity/services/activity.service.ts rename server/src/core/comment/{resolvers => }/comment.resolver.spec.ts (90%) rename server/src/core/comment/{resolvers => }/comment.resolver.ts (95%) rename server/src/core/comment/{services => }/comment.service.spec.ts (100%) rename server/src/core/comment/{services => }/comment.service.ts (100%) delete mode 100644 server/src/core/comment/resolvers/comment-thread.resolver.ts delete mode 100644 server/src/core/comment/services/comment-thread-target.service.ts delete mode 100644 server/src/core/comment/services/comment-thread.service.ts create mode 100644 server/src/database/migrations/20230728061715_complete_comment_thread_migration/migration.sql diff --git a/front/src/generated/graphql.tsx b/front/src/generated/graphql.tsx index 1a21244b7..fc47353bb 100644 --- a/front/src/generated/graphql.tsx +++ b/front/src/generated/graphql.tsx @@ -18,11 +18,414 @@ export type Scalars = { Upload: any; }; +export type Activity = { + __typename?: 'Activity'; + activityTargets?: Maybe>; + assignee?: Maybe; + assigneeId?: Maybe; + attachments?: Maybe>; + author: User; + authorId: Scalars['String']; + body?: Maybe; + comments?: Maybe>; + completedAt?: Maybe; + createdAt: Scalars['DateTime']; + dueAt?: Maybe; + id: Scalars['ID']; + reminderAt?: Maybe; + title?: Maybe; + type: ActivityType; + updatedAt: Scalars['DateTime']; +}; + +export type ActivityCreateInput = { + activityTargets?: InputMaybe; + assignee?: InputMaybe; + attachments?: InputMaybe; + author: UserCreateNestedOneWithoutAuthoredActivitiesInput; + body?: InputMaybe; + comments?: InputMaybe; + completedAt?: InputMaybe; + createdAt?: InputMaybe; + dueAt?: InputMaybe; + id?: InputMaybe; + reminderAt?: InputMaybe; + title?: InputMaybe; + type?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityCreateNestedOneWithoutActivityTargetsInput = { + connect?: InputMaybe; +}; + +export type ActivityCreateNestedOneWithoutCommentsInput = { + connect?: InputMaybe; +}; + +export type ActivityListRelationFilter = { + every?: InputMaybe; + none?: InputMaybe; + some?: InputMaybe; +}; + +export type ActivityOrderByRelationAggregateInput = { + _count?: InputMaybe; +}; + +export type ActivityOrderByWithRelationInput = { + activityTargets?: InputMaybe; + assignee?: InputMaybe; + assigneeId?: InputMaybe; + attachments?: InputMaybe; + author?: InputMaybe; + authorId?: InputMaybe; + body?: InputMaybe; + comments?: InputMaybe; + completedAt?: InputMaybe; + createdAt?: InputMaybe; + dueAt?: InputMaybe; + id?: InputMaybe; + reminderAt?: InputMaybe; + title?: InputMaybe; + type?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityRelationFilter = { + is?: InputMaybe; + isNot?: InputMaybe; +}; + +export enum ActivityScalarFieldEnum { + AssigneeId = 'assigneeId', + AuthorId = 'authorId', + Body = 'body', + CompletedAt = 'completedAt', + CreatedAt = 'createdAt', + DeletedAt = 'deletedAt', + DueAt = 'dueAt', + Id = 'id', + ReminderAt = 'reminderAt', + Title = 'title', + Type = 'type', + UpdatedAt = 'updatedAt', + WorkspaceId = 'workspaceId' +} + +export type ActivityTarget = { + __typename?: 'ActivityTarget'; + activity: Activity; + activityId: Scalars['String']; + commentableId: Scalars['String']; + commentableType: CommentableType; + company?: Maybe; + companyId?: Maybe; + createdAt: Scalars['DateTime']; + id: Scalars['ID']; + person?: Maybe; + personId?: Maybe; + updatedAt: Scalars['DateTime']; +}; + +export type ActivityTargetCreateManyActivityInput = { + commentableId: Scalars['String']; + commentableType: CommentableType; + companyId?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + personId?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetCreateManyActivityInputEnvelope = { + data: Array; + skipDuplicates?: InputMaybe; +}; + +export type ActivityTargetCreateManyCompanyInput = { + activityId: Scalars['String']; + commentableId: Scalars['String']; + commentableType: CommentableType; + createdAt?: InputMaybe; + id?: InputMaybe; + personId?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetCreateManyCompanyInputEnvelope = { + data: Array; + skipDuplicates?: InputMaybe; +}; + +export type ActivityTargetCreateManyPersonInput = { + activityId: Scalars['String']; + commentableId: Scalars['String']; + commentableType: CommentableType; + companyId?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetCreateManyPersonInputEnvelope = { + data: Array; + skipDuplicates?: InputMaybe; +}; + +export type ActivityTargetCreateManyWorkspaceInput = { + activityId: Scalars['String']; + commentableId: Scalars['String']; + commentableType: CommentableType; + companyId?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + personId?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetCreateManyWorkspaceInputEnvelope = { + data: Array; + skipDuplicates?: InputMaybe; +}; + +export type ActivityTargetCreateNestedManyWithoutActivityInput = { + connect?: InputMaybe>; + connectOrCreate?: InputMaybe>; + create?: InputMaybe>; + createMany?: InputMaybe; +}; + +export type ActivityTargetCreateNestedManyWithoutCompanyInput = { + connect?: InputMaybe>; + connectOrCreate?: InputMaybe>; + create?: InputMaybe>; + createMany?: InputMaybe; +}; + +export type ActivityTargetCreateNestedManyWithoutPersonInput = { + connect?: InputMaybe>; + connectOrCreate?: InputMaybe>; + create?: InputMaybe>; + createMany?: InputMaybe; +}; + +export type ActivityTargetCreateOrConnectWithoutActivityInput = { + create: ActivityTargetCreateWithoutActivityInput; + where: ActivityTargetWhereUniqueInput; +}; + +export type ActivityTargetCreateOrConnectWithoutCompanyInput = { + create: ActivityTargetCreateWithoutCompanyInput; + where: ActivityTargetWhereUniqueInput; +}; + +export type ActivityTargetCreateOrConnectWithoutPersonInput = { + create: ActivityTargetCreateWithoutPersonInput; + where: ActivityTargetWhereUniqueInput; +}; + +export type ActivityTargetCreateOrConnectWithoutWorkspaceInput = { + create: ActivityTargetCreateWithoutWorkspaceInput; + where: ActivityTargetWhereUniqueInput; +}; + +export type ActivityTargetCreateWithoutActivityInput = { + commentableId: Scalars['String']; + commentableType: CommentableType; + company?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + person?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetCreateWithoutCompanyInput = { + activity: ActivityCreateNestedOneWithoutActivityTargetsInput; + commentableId: Scalars['String']; + commentableType: CommentableType; + createdAt?: InputMaybe; + id?: InputMaybe; + person?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetCreateWithoutPersonInput = { + activity: ActivityCreateNestedOneWithoutActivityTargetsInput; + commentableId: Scalars['String']; + commentableType: CommentableType; + company?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetCreateWithoutWorkspaceInput = { + activity: ActivityCreateNestedOneWithoutActivityTargetsInput; + commentableId: Scalars['String']; + commentableType: CommentableType; + company?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + person?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetListRelationFilter = { + every?: InputMaybe; + none?: InputMaybe; + some?: InputMaybe; +}; + +export type ActivityTargetOrderByRelationAggregateInput = { + _count?: InputMaybe; +}; + +export type ActivityTargetScalarWhereInput = { + AND?: InputMaybe>; + NOT?: InputMaybe>; + OR?: InputMaybe>; + activityId?: InputMaybe; + commentableId?: InputMaybe; + commentableType?: InputMaybe; + companyId?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + personId?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetUpdateManyWithoutActivityNestedInput = { + connect?: InputMaybe>; + connectOrCreate?: InputMaybe>; + create?: InputMaybe>; + createMany?: InputMaybe; + delete?: InputMaybe>; + deleteMany?: InputMaybe>; + disconnect?: InputMaybe>; + set?: InputMaybe>; +}; + +export type ActivityTargetUpdateManyWithoutCompanyNestedInput = { + connect?: InputMaybe>; + connectOrCreate?: InputMaybe>; + create?: InputMaybe>; + createMany?: InputMaybe; + delete?: InputMaybe>; + deleteMany?: InputMaybe>; + disconnect?: InputMaybe>; + set?: InputMaybe>; +}; + +export type ActivityTargetUpdateManyWithoutPersonNestedInput = { + connect?: InputMaybe>; + connectOrCreate?: InputMaybe>; + create?: InputMaybe>; + createMany?: InputMaybe; + delete?: InputMaybe>; + deleteMany?: InputMaybe>; + disconnect?: InputMaybe>; + set?: InputMaybe>; +}; + +export type ActivityTargetUpdateManyWithoutWorkspaceNestedInput = { + connect?: InputMaybe>; + connectOrCreate?: InputMaybe>; + create?: InputMaybe>; + createMany?: InputMaybe; + delete?: InputMaybe>; + deleteMany?: InputMaybe>; + disconnect?: InputMaybe>; + set?: InputMaybe>; +}; + +export type ActivityTargetWhereInput = { + AND?: InputMaybe>; + NOT?: InputMaybe>; + OR?: InputMaybe>; + activity?: InputMaybe; + activityId?: InputMaybe; + commentableId?: InputMaybe; + commentableType?: InputMaybe; + company?: InputMaybe; + companyId?: InputMaybe; + createdAt?: InputMaybe; + id?: InputMaybe; + person?: InputMaybe; + personId?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityTargetWhereUniqueInput = { + id?: InputMaybe; +}; + export enum ActivityType { Note = 'Note', Task = 'Task' } +export type ActivityUpdateInput = { + activityTargets?: InputMaybe; + assignee?: InputMaybe; + attachments?: InputMaybe; + author?: InputMaybe; + body?: InputMaybe; + comments?: InputMaybe; + completedAt?: InputMaybe; + createdAt?: InputMaybe; + dueAt?: InputMaybe; + id?: InputMaybe; + reminderAt?: InputMaybe; + title?: InputMaybe; + type?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityUpdateManyWithoutAssigneeNestedInput = { + connect?: InputMaybe>; + disconnect?: InputMaybe>; + set?: InputMaybe>; +}; + +export type ActivityUpdateManyWithoutAuthorNestedInput = { + connect?: InputMaybe>; + disconnect?: InputMaybe>; + set?: InputMaybe>; +}; + +export type ActivityUpdateManyWithoutWorkspaceNestedInput = { + connect?: InputMaybe>; + disconnect?: InputMaybe>; + set?: InputMaybe>; +}; + +export type ActivityWhereInput = { + AND?: InputMaybe>; + NOT?: InputMaybe>; + OR?: InputMaybe>; + activityTargets?: InputMaybe; + assignee?: InputMaybe; + assigneeId?: InputMaybe; + attachments?: InputMaybe; + author?: InputMaybe; + authorId?: InputMaybe; + body?: InputMaybe; + comments?: InputMaybe; + completedAt?: InputMaybe; + createdAt?: InputMaybe; + dueAt?: InputMaybe; + id?: InputMaybe; + reminderAt?: InputMaybe; + title?: InputMaybe; + type?: InputMaybe; + updatedAt?: InputMaybe; +}; + +export type ActivityWhereUniqueInput = { + id?: InputMaybe; +}; + export type AffectedRows = { __typename?: 'AffectedRows'; count: Scalars['Int']; @@ -36,7 +439,7 @@ export type Analytics = { export type Attachment = { __typename?: 'Attachment'; - activity: CommentThread; + activity: Activity; activityId: Scalars['String']; author: User; authorId: Scalars['String']; @@ -95,7 +498,7 @@ export type AttachmentWhereInput = { AND?: InputMaybe>; NOT?: InputMaybe>; OR?: InputMaybe>; - activity?: InputMaybe; + activity?: InputMaybe; activityId?: InputMaybe; author?: InputMaybe; authorId?: InputMaybe; @@ -156,26 +559,26 @@ export enum ColorScheme { export type Comment = { __typename?: 'Comment'; + activity: Activity; + activityId: Scalars['String']; author: User; authorId: Scalars['String']; body: Scalars['String']; - commentThread: CommentThread; - commentThreadId: Scalars['String']; createdAt: Scalars['DateTime']; id: Scalars['ID']; updatedAt: Scalars['DateTime']; }; export type CommentCreateInput = { + activity: ActivityCreateNestedOneWithoutCommentsInput; author: UserCreateNestedOneWithoutCommentsInput; body: Scalars['String']; - commentThread: CommentThreadCreateNestedOneWithoutCommentsInput; createdAt?: InputMaybe; id?: InputMaybe; updatedAt?: InputMaybe; }; -export type CommentCreateNestedManyWithoutCommentThreadInput = { +export type CommentCreateNestedManyWithoutActivityInput = { connect?: InputMaybe>; }; @@ -189,303 +592,13 @@ export type CommentOrderByRelationAggregateInput = { _count?: InputMaybe; }; -export type CommentThread = { - __typename?: 'CommentThread'; - assignee?: Maybe; - assigneeId?: Maybe; - attachments?: Maybe>; - author: User; - authorId: Scalars['String']; - body?: Maybe; - commentThreadTargets?: Maybe>; - comments?: Maybe>; - completedAt?: Maybe; - createdAt: Scalars['DateTime']; - dueAt?: Maybe; - id: Scalars['ID']; - reminderAt?: Maybe; - title?: Maybe; - type: ActivityType; - updatedAt: Scalars['DateTime']; -}; - -export type CommentThreadCreateInput = { - assignee?: InputMaybe; - attachments?: InputMaybe; - author: UserCreateNestedOneWithoutAuthoredCommentThreadsInput; - body?: InputMaybe; - commentThreadTargets?: InputMaybe; - comments?: InputMaybe; - completedAt?: InputMaybe; - createdAt?: InputMaybe; - dueAt?: InputMaybe; - id?: InputMaybe; - reminderAt?: InputMaybe; - title?: InputMaybe; - type?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadCreateNestedOneWithoutCommentThreadTargetsInput = { - connect?: InputMaybe; -}; - -export type CommentThreadCreateNestedOneWithoutCommentsInput = { - connect?: InputMaybe; -}; - -export type CommentThreadListRelationFilter = { - every?: InputMaybe; - none?: InputMaybe; - some?: InputMaybe; -}; - -export type CommentThreadOrderByRelationAggregateInput = { - _count?: InputMaybe; -}; - -export type CommentThreadOrderByWithRelationInput = { - assignee?: InputMaybe; - assigneeId?: InputMaybe; - attachments?: InputMaybe; - author?: InputMaybe; - authorId?: InputMaybe; - body?: InputMaybe; - commentThreadTargets?: InputMaybe; - comments?: InputMaybe; - completedAt?: InputMaybe; - createdAt?: InputMaybe; - dueAt?: InputMaybe; - id?: InputMaybe; - reminderAt?: InputMaybe; - title?: InputMaybe; - type?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadRelationFilter = { - is?: InputMaybe; - isNot?: InputMaybe; -}; - -export enum CommentThreadScalarFieldEnum { - AssigneeId = 'assigneeId', - AuthorId = 'authorId', - Body = 'body', - CompletedAt = 'completedAt', - CreatedAt = 'createdAt', - DeletedAt = 'deletedAt', - DueAt = 'dueAt', - Id = 'id', - ReminderAt = 'reminderAt', - Title = 'title', - Type = 'type', - UpdatedAt = 'updatedAt', - WorkspaceId = 'workspaceId' -} - -export type CommentThreadTarget = { - __typename?: 'CommentThreadTarget'; - commentThread: CommentThread; - commentThreadId: Scalars['String']; - commentableId: Scalars['String']; - commentableType: CommentableType; - createdAt: Scalars['DateTime']; - id: Scalars['ID']; - updatedAt: Scalars['DateTime']; - workspace?: Maybe; -}; - -export type CommentThreadTargetCreateManyCommentThreadInput = { - commentableId: Scalars['String']; - commentableType: CommentableType; - createdAt?: InputMaybe; - id?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadTargetCreateManyCommentThreadInputEnvelope = { - data: Array; - skipDuplicates?: InputMaybe; -}; - -export type CommentThreadTargetCreateManyWorkspaceInput = { - commentThreadId: Scalars['String']; - commentableId: Scalars['String']; - commentableType: CommentableType; - createdAt?: InputMaybe; - id?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadTargetCreateManyWorkspaceInputEnvelope = { - data: Array; - skipDuplicates?: InputMaybe; -}; - -export type CommentThreadTargetCreateNestedManyWithoutCommentThreadInput = { - connect?: InputMaybe>; - connectOrCreate?: InputMaybe>; - create?: InputMaybe>; - createMany?: InputMaybe; -}; - -export type CommentThreadTargetCreateOrConnectWithoutCommentThreadInput = { - create: CommentThreadTargetCreateWithoutCommentThreadInput; - where: CommentThreadTargetWhereUniqueInput; -}; - -export type CommentThreadTargetCreateOrConnectWithoutWorkspaceInput = { - create: CommentThreadTargetCreateWithoutWorkspaceInput; - where: CommentThreadTargetWhereUniqueInput; -}; - -export type CommentThreadTargetCreateWithoutCommentThreadInput = { - commentableId: Scalars['String']; - commentableType: CommentableType; - createdAt?: InputMaybe; - id?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadTargetCreateWithoutWorkspaceInput = { - commentThread: CommentThreadCreateNestedOneWithoutCommentThreadTargetsInput; - commentableId: Scalars['String']; - commentableType: CommentableType; - createdAt?: InputMaybe; - id?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadTargetListRelationFilter = { - every?: InputMaybe; - none?: InputMaybe; - some?: InputMaybe; -}; - -export type CommentThreadTargetOrderByRelationAggregateInput = { - _count?: InputMaybe; -}; - -export type CommentThreadTargetScalarWhereInput = { - AND?: InputMaybe>; - NOT?: InputMaybe>; - OR?: InputMaybe>; - commentThreadId?: InputMaybe; - commentableId?: InputMaybe; - commentableType?: InputMaybe; - createdAt?: InputMaybe; - id?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadTargetUpdateManyWithoutCommentThreadNestedInput = { - connect?: InputMaybe>; - connectOrCreate?: InputMaybe>; - create?: InputMaybe>; - createMany?: InputMaybe; - delete?: InputMaybe>; - deleteMany?: InputMaybe>; - disconnect?: InputMaybe>; - set?: InputMaybe>; -}; - -export type CommentThreadTargetUpdateManyWithoutWorkspaceNestedInput = { - connect?: InputMaybe>; - connectOrCreate?: InputMaybe>; - create?: InputMaybe>; - createMany?: InputMaybe; - delete?: InputMaybe>; - deleteMany?: InputMaybe>; - disconnect?: InputMaybe>; - set?: InputMaybe>; -}; - -export type CommentThreadTargetWhereInput = { - AND?: InputMaybe>; - NOT?: InputMaybe>; - OR?: InputMaybe>; - commentThread?: InputMaybe; - commentThreadId?: InputMaybe; - commentableId?: InputMaybe; - commentableType?: InputMaybe; - createdAt?: InputMaybe; - id?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadTargetWhereUniqueInput = { - id?: InputMaybe; -}; - -export type CommentThreadUpdateInput = { - assignee?: InputMaybe; - attachments?: InputMaybe; - author?: InputMaybe; - body?: InputMaybe; - commentThreadTargets?: InputMaybe; - comments?: InputMaybe; - completedAt?: InputMaybe; - createdAt?: InputMaybe; - dueAt?: InputMaybe; - id?: InputMaybe; - reminderAt?: InputMaybe; - title?: InputMaybe; - type?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadUpdateManyWithoutAssigneeNestedInput = { - connect?: InputMaybe>; - disconnect?: InputMaybe>; - set?: InputMaybe>; -}; - -export type CommentThreadUpdateManyWithoutAuthorNestedInput = { - connect?: InputMaybe>; - disconnect?: InputMaybe>; - set?: InputMaybe>; -}; - -export type CommentThreadUpdateManyWithoutWorkspaceNestedInput = { - connect?: InputMaybe>; - disconnect?: InputMaybe>; - set?: InputMaybe>; -}; - -export type CommentThreadWhereInput = { - AND?: InputMaybe>; - NOT?: InputMaybe>; - OR?: InputMaybe>; - assignee?: InputMaybe; - assigneeId?: InputMaybe; - attachments?: InputMaybe; - author?: InputMaybe; - authorId?: InputMaybe; - body?: InputMaybe; - commentThreadTargets?: InputMaybe; - comments?: InputMaybe; - completedAt?: InputMaybe; - createdAt?: InputMaybe; - dueAt?: InputMaybe; - id?: InputMaybe; - reminderAt?: InputMaybe; - title?: InputMaybe; - type?: InputMaybe; - updatedAt?: InputMaybe; -}; - -export type CommentThreadWhereUniqueInput = { - id?: InputMaybe; -}; - -export type CommentUpdateManyWithoutAuthorNestedInput = { +export type CommentUpdateManyWithoutActivityNestedInput = { connect?: InputMaybe>; disconnect?: InputMaybe>; set?: InputMaybe>; }; -export type CommentUpdateManyWithoutCommentThreadNestedInput = { +export type CommentUpdateManyWithoutAuthorNestedInput = { connect?: InputMaybe>; disconnect?: InputMaybe>; set?: InputMaybe>; @@ -501,11 +614,11 @@ export type CommentWhereInput = { AND?: InputMaybe>; NOT?: InputMaybe>; OR?: InputMaybe>; + activity?: InputMaybe; + activityId?: InputMaybe; author?: InputMaybe; authorId?: InputMaybe; body?: InputMaybe; - commentThread?: InputMaybe; - commentThreadId?: InputMaybe; createdAt?: InputMaybe; id?: InputMaybe; updatedAt?: InputMaybe; @@ -522,11 +635,12 @@ export enum CommentableType { export type Company = { __typename?: 'Company'; - _commentThreadCount: Scalars['Int']; + ActivityTarget?: Maybe>; + _activityCount: Scalars['Int']; accountOwner?: Maybe; accountOwnerId?: Maybe; + activities: Array; address: Scalars['String']; - commentThreads: Array; comments: Array; createdAt: Scalars['DateTime']; domainName: Scalars['String']; @@ -539,6 +653,7 @@ export type Company = { }; export type CompanyCreateInput = { + ActivityTarget?: InputMaybe; accountOwner?: InputMaybe; address: Scalars['String']; createdAt?: InputMaybe; @@ -551,6 +666,10 @@ export type CompanyCreateInput = { updatedAt?: InputMaybe; }; +export type CompanyCreateNestedOneWithoutActivityTargetInput = { + connect?: InputMaybe; +}; + export type CompanyCreateNestedOneWithoutPeopleInput = { connect?: InputMaybe; }; @@ -566,6 +685,7 @@ export type CompanyOrderByRelationAggregateInput = { }; export type CompanyOrderByWithRelationInput = { + ActivityTarget?: InputMaybe; accountOwner?: InputMaybe; accountOwnerId?: InputMaybe; address?: InputMaybe; @@ -599,6 +719,7 @@ export enum CompanyScalarFieldEnum { } export type CompanyUpdateInput = { + ActivityTarget?: InputMaybe; accountOwner?: InputMaybe; address?: InputMaybe; createdAt?: InputMaybe; @@ -630,6 +751,7 @@ export type CompanyUpdateOneWithoutPeopleNestedInput = { export type CompanyWhereInput = { AND?: InputMaybe>; + ActivityTarget?: InputMaybe; NOT?: InputMaybe>; OR?: InputMaybe>; accountOwner?: InputMaybe; @@ -759,20 +881,20 @@ export type Mutation = { __typename?: 'Mutation'; challenge: LoginToken; createEvent: Analytics; + createOneActivity: Activity; createOneComment: Comment; - createOneCommentThread: CommentThread; createOneCompany: Company; createOnePerson: Person; createOnePipelineProgress: PipelineProgress; deleteCurrentWorkspace: Workspace; - deleteManyCommentThreads: AffectedRows; + deleteManyActivities: AffectedRows; deleteManyCompany: AffectedRows; deleteManyPerson: AffectedRows; deleteManyPipelineProgress: AffectedRows; deleteWorkspaceMember: WorkspaceMember; renewToken: AuthTokens; signUp: LoginToken; - updateOneCommentThread: CommentThread; + updateOneActivity: Activity; updateOneCompany?: Maybe; updateOnePerson?: Maybe; updateOnePipelineProgress?: Maybe; @@ -801,13 +923,13 @@ export type MutationCreateEventArgs = { }; -export type MutationCreateOneCommentArgs = { - data: CommentCreateInput; +export type MutationCreateOneActivityArgs = { + data: ActivityCreateInput; }; -export type MutationCreateOneCommentThreadArgs = { - data: CommentThreadCreateInput; +export type MutationCreateOneCommentArgs = { + data: CommentCreateInput; }; @@ -826,8 +948,8 @@ export type MutationCreateOnePipelineProgressArgs = { }; -export type MutationDeleteManyCommentThreadsArgs = { - where?: InputMaybe; +export type MutationDeleteManyActivitiesArgs = { + where?: InputMaybe; }; @@ -863,9 +985,9 @@ export type MutationSignUpArgs = { }; -export type MutationUpdateOneCommentThreadArgs = { - data: CommentThreadUpdateInput; - where: CommentThreadWhereUniqueInput; +export type MutationUpdateOneActivityArgs = { + data: ActivityUpdateInput; + where: ActivityWhereUniqueInput; }; @@ -1056,9 +1178,10 @@ export type NestedStringNullableFilter = { export type Person = { __typename?: 'Person'; - _commentThreadCount: Scalars['Int']; + ActivityTarget?: Maybe>; + _activityCount: Scalars['Int']; + activities: Array; city?: Maybe; - commentThreads: Array; comments: Array; company?: Maybe; companyId?: Maybe; @@ -1076,6 +1199,7 @@ export type Person = { }; export type PersonCreateInput = { + ActivityTarget?: InputMaybe; city?: InputMaybe; company?: InputMaybe; createdAt?: InputMaybe; @@ -1094,6 +1218,10 @@ export type PersonCreateNestedManyWithoutCompanyInput = { connect?: InputMaybe>; }; +export type PersonCreateNestedOneWithoutActivityTargetInput = { + connect?: InputMaybe; +}; + export type PersonCreateNestedOneWithoutPipelineProgressesInput = { connect?: InputMaybe; }; @@ -1109,6 +1237,7 @@ export type PersonOrderByRelationAggregateInput = { }; export type PersonOrderByWithRelationInput = { + ActivityTarget?: InputMaybe; city?: InputMaybe; company?: InputMaybe; companyId?: InputMaybe; @@ -1146,6 +1275,7 @@ export enum PersonScalarFieldEnum { } export type PersonUpdateInput = { + ActivityTarget?: InputMaybe; city?: InputMaybe; company?: InputMaybe; createdAt?: InputMaybe; @@ -1179,6 +1309,7 @@ export type PersonUpdateOneWithoutPipelineProgressesNestedInput = { export type PersonWhereInput = { AND?: InputMaybe>; + ActivityTarget?: InputMaybe; NOT?: InputMaybe>; OR?: InputMaybe>; city?: InputMaybe; @@ -1523,7 +1654,7 @@ export type Query = { clientConfig: ClientConfig; currentUser: User; currentWorkspace: Workspace; - findManyCommentThreads: Array; + findManyActivities: Array; findManyCompany: Array; findManyPerson: Array; findManyPipeline: Array; @@ -1547,13 +1678,13 @@ export type QueryCheckWorkspaceInviteHashIsValidArgs = { }; -export type QueryFindManyCommentThreadsArgs = { - cursor?: InputMaybe; - distinct?: InputMaybe>; - orderBy?: InputMaybe>; +export type QueryFindManyActivitiesArgs = { + cursor?: InputMaybe; + distinct?: InputMaybe>; + orderBy?: InputMaybe>; skip?: InputMaybe; take?: InputMaybe; - where?: InputMaybe; + where?: InputMaybe; }; @@ -1694,9 +1825,9 @@ export type Telemetry = { export type User = { __typename?: 'User'; - assignedCommentThreads?: Maybe>; + assignedActivities?: Maybe>; + authoredActivities?: Maybe>; authoredAttachments?: Maybe>; - authoredCommentThreads?: Maybe>; avatarUrl?: Maybe; comments?: Maybe>; companies?: Maybe>; @@ -1718,11 +1849,11 @@ export type User = { workspaceMember?: Maybe; }; -export type UserCreateNestedOneWithoutAssignedCommentThreadsInput = { +export type UserCreateNestedOneWithoutAssignedActivitiesInput = { connect?: InputMaybe; }; -export type UserCreateNestedOneWithoutAuthoredCommentThreadsInput = { +export type UserCreateNestedOneWithoutAuthoredActivitiesInput = { connect?: InputMaybe; }; @@ -1740,9 +1871,9 @@ export type UserExists = { }; export type UserOrderByWithRelationInput = { - assignedCommentThreads?: InputMaybe; + assignedActivities?: InputMaybe; + authoredActivities?: InputMaybe; authoredAttachments?: InputMaybe; - authoredCommentThreads?: InputMaybe; avatarUrl?: InputMaybe; comments?: InputMaybe; companies?: InputMaybe; @@ -1835,9 +1966,9 @@ export type UserSettingsWhereInput = { }; export type UserUpdateInput = { - assignedCommentThreads?: InputMaybe; + assignedActivities?: InputMaybe; + authoredActivities?: InputMaybe; authoredAttachments?: InputMaybe; - authoredCommentThreads?: InputMaybe; avatarUrl?: InputMaybe; comments?: InputMaybe; companies?: InputMaybe; @@ -1856,11 +1987,11 @@ export type UserUpdateInput = { updatedAt?: InputMaybe; }; -export type UserUpdateOneRequiredWithoutAuthoredCommentThreadsNestedInput = { +export type UserUpdateOneRequiredWithoutAuthoredActivitiesNestedInput = { connect?: InputMaybe; }; -export type UserUpdateOneWithoutAssignedCommentThreadsNestedInput = { +export type UserUpdateOneWithoutAssignedActivitiesNestedInput = { connect?: InputMaybe; disconnect?: InputMaybe; }; @@ -1874,9 +2005,9 @@ export type UserWhereInput = { AND?: InputMaybe>; NOT?: InputMaybe>; OR?: InputMaybe>; - assignedCommentThreads?: InputMaybe; + assignedActivities?: InputMaybe; + authoredActivities?: InputMaybe; authoredAttachments?: InputMaybe; - authoredCommentThreads?: InputMaybe; avatarUrl?: InputMaybe; comments?: InputMaybe; companies?: InputMaybe; @@ -1971,8 +2102,8 @@ export type ViewFieldWhereUniqueInput = { export type Workspace = { __typename?: 'Workspace'; Attachment?: Maybe>; - CommentThreadTarget?: Maybe>; - commentThreads?: Maybe>; + activities?: Maybe>; + activityTargets?: Maybe>; comments?: Maybe>; companies?: Maybe>; createdAt: Scalars['DateTime']; @@ -2046,8 +2177,8 @@ export type WorkspaceMemberWhereUniqueInput = { export type WorkspaceUpdateInput = { Attachment?: InputMaybe; - CommentThreadTarget?: InputMaybe; - commentThreads?: InputMaybe; + activities?: InputMaybe; + activityTargets?: InputMaybe; comments?: InputMaybe; companies?: InputMaybe; createdAt?: InputMaybe; @@ -2069,65 +2200,65 @@ export type CreateCommentMutationVariables = Exact<{ commentId: Scalars['String']; commentText: Scalars['String']; authorId: Scalars['String']; - commentThreadId: Scalars['String']; + activityId: Scalars['String']; createdAt: Scalars['DateTime']; }>; -export type CreateCommentMutation = { __typename?: 'Mutation', createOneComment: { __typename?: 'Comment', id: string, createdAt: string, body: string, commentThreadId: string, author: { __typename?: 'User', id: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } } }; +export type CreateCommentMutation = { __typename?: 'Mutation', createOneComment: { __typename?: 'Comment', id: string, createdAt: string, body: string, activityId: string, author: { __typename?: 'User', id: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } } }; -export type CreateCommentThreadMutationVariables = Exact<{ - commentThreadId: Scalars['String']; +export type CreateActivityMutationVariables = Exact<{ + activityId: Scalars['String']; body?: InputMaybe; title?: InputMaybe; type: ActivityType; authorId: Scalars['String']; createdAt: Scalars['DateTime']; - commentThreadTargetArray: Array | CommentThreadTargetCreateManyCommentThreadInput; + activityTargetArray: Array | ActivityTargetCreateManyActivityInput; }>; -export type CreateCommentThreadMutation = { __typename?: 'Mutation', createOneCommentThread: { __typename?: 'CommentThread', id: string, createdAt: string, updatedAt: string, authorId: string, type: ActivityType, commentThreadTargets?: Array<{ __typename?: 'CommentThreadTarget', id: string, createdAt: string, updatedAt: string, commentThreadId: string, commentableType: CommentableType, commentableId: string }> | null, comments?: Array<{ __typename?: 'Comment', id: string, createdAt: string, updatedAt: string, body: string, author: { __typename?: 'User', id: string } }> | null } }; +export type CreateActivityMutation = { __typename?: 'Mutation', createOneActivity: { __typename?: 'Activity', id: string, createdAt: string, updatedAt: string, authorId: string, type: ActivityType, activityTargets?: Array<{ __typename?: 'ActivityTarget', id: string, createdAt: string, updatedAt: string, activityId: string, commentableType: CommentableType, commentableId: string }> | null, comments?: Array<{ __typename?: 'Comment', id: string, createdAt: string, updatedAt: string, body: string, author: { __typename?: 'User', id: string } }> | null } }; -export type GetCommentThreadsByTargetsQueryVariables = Exact<{ - commentThreadTargetIds: Array | Scalars['String']; - orderBy?: InputMaybe | CommentThreadOrderByWithRelationInput>; +export type GetActivitiesByTargetsQueryVariables = Exact<{ + activityTargetIds: Array | Scalars['String']; + orderBy?: InputMaybe | ActivityOrderByWithRelationInput>; }>; -export type GetCommentThreadsByTargetsQuery = { __typename?: 'Query', findManyCommentThreads: Array<{ __typename?: 'CommentThread', id: string, createdAt: string, title?: string | null, body?: string | null, type: ActivityType, completedAt?: string | null, author: { __typename?: 'User', id: string, firstName?: string | null, lastName?: string | null, displayName: string }, comments?: Array<{ __typename?: 'Comment', id: string, body: string, createdAt: string, updatedAt: string, author: { __typename?: 'User', id: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } }> | null, commentThreadTargets?: Array<{ __typename?: 'CommentThreadTarget', id: string, commentableId: string, commentableType: CommentableType }> | null }> }; +export type GetActivitiesByTargetsQuery = { __typename?: 'Query', findManyActivities: Array<{ __typename?: 'Activity', id: string, createdAt: string, title?: string | null, body?: string | null, type: ActivityType, completedAt?: string | null, author: { __typename?: 'User', id: string, firstName?: string | null, lastName?: string | null, displayName: string }, comments?: Array<{ __typename?: 'Comment', id: string, body: string, createdAt: string, updatedAt: string, author: { __typename?: 'User', id: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } }> | null, activityTargets?: Array<{ __typename?: 'ActivityTarget', id: string, commentableType: CommentableType, commentableId: string }> | null }> }; -export type GetCommentThreadQueryVariables = Exact<{ - commentThreadId: Scalars['String']; +export type GetActivityQueryVariables = Exact<{ + activityId: Scalars['String']; }>; -export type GetCommentThreadQuery = { __typename?: 'Query', findManyCommentThreads: Array<{ __typename?: 'CommentThread', id: string, createdAt: string, body?: string | null, title?: string | null, type: ActivityType, completedAt?: string | null, author: { __typename?: 'User', id: string, firstName?: string | null, lastName?: string | null, displayName: string }, comments?: Array<{ __typename?: 'Comment', id: string, body: string, createdAt: string, updatedAt: string, author: { __typename?: 'User', id: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } }> | null, commentThreadTargets?: Array<{ __typename?: 'CommentThreadTarget', id: string, commentableId: string, commentableType: CommentableType }> | null }> }; +export type GetActivityQuery = { __typename?: 'Query', findManyActivities: Array<{ __typename?: 'Activity', id: string, createdAt: string, body?: string | null, title?: string | null, type: ActivityType, completedAt?: string | null, author: { __typename?: 'User', id: string, firstName?: string | null, lastName?: string | null, displayName: string }, comments?: Array<{ __typename?: 'Comment', id: string, body: string, createdAt: string, updatedAt: string, author: { __typename?: 'User', id: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } }> | null, activityTargets?: Array<{ __typename?: 'ActivityTarget', id: string, commentableType: CommentableType, commentableId: string }> | null }> }; -export type AddCommentThreadTargetsOnCommentThreadMutationVariables = Exact<{ - commentThreadId: Scalars['String']; - commentThreadTargetInputs: Array | CommentThreadTargetCreateManyCommentThreadInput; +export type AddActivityTargetsOnActivityMutationVariables = Exact<{ + activityId: Scalars['String']; + activityTargetInputs: Array | ActivityTargetCreateManyActivityInput; }>; -export type AddCommentThreadTargetsOnCommentThreadMutation = { __typename?: 'Mutation', updateOneCommentThread: { __typename?: 'CommentThread', id: string, createdAt: string, updatedAt: string, commentThreadTargets?: Array<{ __typename?: 'CommentThreadTarget', id: string, createdAt: string, updatedAt: string, commentableType: CommentableType, commentableId: string }> | null } }; +export type AddActivityTargetsOnActivityMutation = { __typename?: 'Mutation', updateOneActivity: { __typename?: 'Activity', id: string, createdAt: string, updatedAt: string, activityTargets?: Array<{ __typename?: 'ActivityTarget', id: string, createdAt: string, updatedAt: string, commentableType: CommentableType, commentableId: string }> | null } }; -export type RemoveCommentThreadTargetsOnCommentThreadMutationVariables = Exact<{ - commentThreadId: Scalars['String']; - commentThreadTargetIds: Array | Scalars['String']; +export type RemoveActivityTargetsOnActivityMutationVariables = Exact<{ + activityId: Scalars['String']; + activityTargetIds: Array | Scalars['String']; }>; -export type RemoveCommentThreadTargetsOnCommentThreadMutation = { __typename?: 'Mutation', updateOneCommentThread: { __typename?: 'CommentThread', id: string, createdAt: string, updatedAt: string, commentThreadTargets?: Array<{ __typename?: 'CommentThreadTarget', id: string, createdAt: string, updatedAt: string, commentableType: CommentableType, commentableId: string }> | null } }; +export type RemoveActivityTargetsOnActivityMutation = { __typename?: 'Mutation', updateOneActivity: { __typename?: 'Activity', id: string, createdAt: string, updatedAt: string, activityTargets?: Array<{ __typename?: 'ActivityTarget', id: string, createdAt: string, updatedAt: string, commentableType: CommentableType, commentableId: string }> | null } }; -export type DeleteCommentThreadMutationVariables = Exact<{ - commentThreadId: Scalars['String']; +export type DeleteActivityMutationVariables = Exact<{ + activityId: Scalars['String']; }>; -export type DeleteCommentThreadMutation = { __typename?: 'Mutation', deleteManyCommentThreads: { __typename?: 'AffectedRows', count: number } }; +export type DeleteActivityMutation = { __typename?: 'Mutation', deleteManyActivities: { __typename?: 'AffectedRows', count: number } }; -export type UpdateCommentThreadMutationVariables = Exact<{ +export type UpdateActivityMutationVariables = Exact<{ id: Scalars['String']; body?: InputMaybe; title?: InputMaybe; @@ -2136,7 +2267,7 @@ export type UpdateCommentThreadMutationVariables = Exact<{ }>; -export type UpdateCommentThreadMutation = { __typename?: 'Mutation', updateOneCommentThread: { __typename?: 'CommentThread', id: string, body?: string | null, title?: string | null, type: ActivityType, completedAt?: string | null } }; +export type UpdateActivityMutation = { __typename?: 'Mutation', updateOneActivity: { __typename?: 'Activity', id: string, body?: string | null, title?: string | null, type: ActivityType, completedAt?: string | null } }; export type UploadAttachmentMutationVariables = Exact<{ file: Scalars['Upload']; @@ -2203,14 +2334,14 @@ export type GetCompaniesQueryVariables = Exact<{ }>; -export type GetCompaniesQuery = { __typename?: 'Query', companies: Array<{ __typename?: 'Company', id: string, domainName: string, name: string, createdAt: string, address: string, linkedinUrl?: string | null, employees?: number | null, _commentThreadCount: number, accountOwner?: { __typename?: 'User', id: string, email: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } | null }> }; +export type GetCompaniesQuery = { __typename?: 'Query', companies: Array<{ __typename?: 'Company', id: string, domainName: string, name: string, createdAt: string, address: string, linkedinUrl?: string | null, employees?: number | null, _activityCount: number, accountOwner?: { __typename?: 'User', id: string, email: string, displayName: string, firstName?: string | null, lastName?: string | null, avatarUrl?: string | null } | null }> }; export type GetCompanyQueryVariables = Exact<{ where: CompanyWhereUniqueInput; }>; -export type GetCompanyQuery = { __typename?: 'Query', findUniqueCompany: { __typename?: 'Company', id: string, domainName: string, name: string, createdAt: string, address: string, linkedinUrl?: string | null, employees?: number | null, _commentThreadCount: number, accountOwner?: { __typename?: 'User', id: string, email: string, displayName: string, avatarUrl?: string | null } | null } }; +export type GetCompanyQuery = { __typename?: 'Query', findUniqueCompany: { __typename?: 'Company', id: string, domainName: string, name: string, createdAt: string, address: string, linkedinUrl?: string | null, employees?: number | null, _activityCount: number, accountOwner?: { __typename?: 'User', id: string, email: string, displayName: string, avatarUrl?: string | null } | null } }; export type UpdateOneCompanyMutationVariables = Exact<{ where: CompanyWhereUniqueInput; @@ -2241,7 +2372,7 @@ export type GetPeopleQueryVariables = Exact<{ }>; -export type GetPeopleQuery = { __typename?: 'Query', people: Array<{ __typename?: 'Person', id: string, phone?: string | null, email?: string | null, city?: string | null, firstName?: string | null, lastName?: string | null, displayName: string, jobTitle?: string | null, linkedinUrl?: string | null, createdAt: string, _commentThreadCount: number, company?: { __typename?: 'Company', id: string, name: string, domainName: string } | null }> }; +export type GetPeopleQuery = { __typename?: 'Query', people: Array<{ __typename?: 'Person', id: string, phone?: string | null, email?: string | null, city?: string | null, firstName?: string | null, lastName?: string | null, displayName: string, jobTitle?: string | null, linkedinUrl?: string | null, createdAt: string, _activityCount: number, company?: { __typename?: 'Company', id: string, name: string, domainName: string } | null }> }; export type GetPersonPhoneByIdQueryVariables = Exact<{ id: Scalars['String']; @@ -2262,7 +2393,7 @@ export type GetPersonNamesAndCommentCountByIdQueryVariables = Exact<{ }>; -export type GetPersonNamesAndCommentCountByIdQuery = { __typename?: 'Query', person: { __typename?: 'Person', id: string, firstName?: string | null, lastName?: string | null, displayName: string, _commentThreadCount: number } }; +export type GetPersonNamesAndCommentCountByIdQuery = { __typename?: 'Query', person: { __typename?: 'Person', id: string, firstName?: string | null, lastName?: string | null, displayName: string, _activityCount: number } }; export type GetPersonCompanyByIdQueryVariables = Exact<{ id: Scalars['String']; @@ -2276,7 +2407,7 @@ export type GetPersonCommentCountByIdQueryVariables = Exact<{ }>; -export type GetPersonCommentCountByIdQuery = { __typename?: 'Query', person: { __typename?: 'Person', id: string, _commentThreadCount: number } }; +export type GetPersonCommentCountByIdQuery = { __typename?: 'Query', person: { __typename?: 'Person', id: string, _activityCount: number } }; export type GetPersonCreatedAtByIdQueryVariables = Exact<{ id: Scalars['String']; @@ -2297,7 +2428,7 @@ export type GetPersonQueryVariables = Exact<{ }>; -export type GetPersonQuery = { __typename?: 'Query', findUniquePerson: { __typename?: 'Person', id: string, firstName?: string | null, lastName?: string | null, displayName: string, email?: string | null, createdAt: string, city?: string | null, jobTitle?: string | null, linkedinUrl?: string | null, phone?: string | null, _commentThreadCount: number, company?: { __typename?: 'Company', id: string, name: string, domainName: string } | null } }; +export type GetPersonQuery = { __typename?: 'Query', findUniquePerson: { __typename?: 'Person', id: string, firstName?: string | null, lastName?: string | null, displayName: string, email?: string | null, createdAt: string, city?: string | null, jobTitle?: string | null, linkedinUrl?: string | null, phone?: string | null, _activityCount: number, company?: { __typename?: 'Company', id: string, name: string, domainName: string } | null } }; export type UpdateOnePersonMutationVariables = Exact<{ where: PersonWhereUniqueInput; @@ -2498,9 +2629,9 @@ export type DeleteCurrentWorkspaceMutation = { __typename?: 'Mutation', deleteCu export const CreateCommentDocument = gql` - mutation CreateComment($commentId: String!, $commentText: String!, $authorId: String!, $commentThreadId: String!, $createdAt: DateTime!) { + mutation CreateComment($commentId: String!, $commentText: String!, $authorId: String!, $activityId: String!, $createdAt: DateTime!) { createOneComment( - data: {id: $commentId, createdAt: $createdAt, body: $commentText, author: {connect: {id: $authorId}}, commentThread: {connect: {id: $commentThreadId}}} + data: {id: $commentId, createdAt: $createdAt, body: $commentText, author: {connect: {id: $authorId}}, activity: {connect: {id: $activityId}}} ) { id createdAt @@ -2512,7 +2643,7 @@ export const CreateCommentDocument = gql` lastName avatarUrl } - commentThreadId + activityId } } `; @@ -2534,7 +2665,7 @@ export type CreateCommentMutationFn = Apollo.MutationFunction; export type CreateCommentMutationResult = Apollo.MutationResult; export type CreateCommentMutationOptions = Apollo.BaseMutationOptions; -export const CreateCommentThreadDocument = gql` - mutation CreateCommentThread($commentThreadId: String!, $body: String, $title: String, $type: ActivityType!, $authorId: String!, $createdAt: DateTime!, $commentThreadTargetArray: [CommentThreadTargetCreateManyCommentThreadInput!]!) { - createOneCommentThread( - data: {id: $commentThreadId, createdAt: $createdAt, updatedAt: $createdAt, author: {connect: {id: $authorId}}, body: $body, title: $title, type: $type, commentThreadTargets: {createMany: {data: $commentThreadTargetArray, skipDuplicates: true}}} +export const CreateActivityDocument = gql` + mutation CreateActivity($activityId: String!, $body: String, $title: String, $type: ActivityType!, $authorId: String!, $createdAt: DateTime!, $activityTargetArray: [ActivityTargetCreateManyActivityInput!]!) { + createOneActivity( + data: {id: $activityId, createdAt: $createdAt, updatedAt: $createdAt, author: {connect: {id: $authorId}}, body: $body, title: $title, type: $type, activityTargets: {createMany: {data: $activityTargetArray, skipDuplicates: true}}} ) { id createdAt updatedAt authorId type - commentThreadTargets { + activityTargets { id createdAt updatedAt - commentThreadId + activityId commentableType commentableId } @@ -2576,43 +2707,43 @@ export const CreateCommentThreadDocument = gql` } } `; -export type CreateCommentThreadMutationFn = Apollo.MutationFunction; +export type CreateActivityMutationFn = Apollo.MutationFunction; /** - * __useCreateCommentThreadMutation__ + * __useCreateActivityMutation__ * - * To run a mutation, you first call `useCreateCommentThreadMutation` within a React component and pass it any options that fit your needs. - * When your component renders, `useCreateCommentThreadMutation` returns a tuple that includes: + * To run a mutation, you first call `useCreateActivityMutation` within a React component and pass it any options that fit your needs. + * When your component renders, `useCreateActivityMutation` returns a tuple that includes: * - A mutate function that you can call at any time to execute the mutation * - An object with fields that represent the current status of the mutation's execution * * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2; * * @example - * const [createCommentThreadMutation, { data, loading, error }] = useCreateCommentThreadMutation({ + * const [createActivityMutation, { data, loading, error }] = useCreateActivityMutation({ * variables: { - * commentThreadId: // value for 'commentThreadId' + * activityId: // value for 'activityId' * body: // value for 'body' * title: // value for 'title' * type: // value for 'type' * authorId: // value for 'authorId' * createdAt: // value for 'createdAt' - * commentThreadTargetArray: // value for 'commentThreadTargetArray' + * activityTargetArray: // value for 'activityTargetArray' * }, * }); */ -export function useCreateCommentThreadMutation(baseOptions?: Apollo.MutationHookOptions) { +export function useCreateActivityMutation(baseOptions?: Apollo.MutationHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useMutation(CreateCommentThreadDocument, options); + return Apollo.useMutation(CreateActivityDocument, options); } -export type CreateCommentThreadMutationHookResult = ReturnType; -export type CreateCommentThreadMutationResult = Apollo.MutationResult; -export type CreateCommentThreadMutationOptions = Apollo.BaseMutationOptions; -export const GetCommentThreadsByTargetsDocument = gql` - query GetCommentThreadsByTargets($commentThreadTargetIds: [String!]!, $orderBy: [CommentThreadOrderByWithRelationInput!]) { - findManyCommentThreads( +export type CreateActivityMutationHookResult = ReturnType; +export type CreateActivityMutationResult = Apollo.MutationResult; +export type CreateActivityMutationOptions = Apollo.BaseMutationOptions; +export const GetActivitiesByTargetsDocument = gql` + query GetActivitiesByTargets($activityTargetIds: [String!]!, $orderBy: [ActivityOrderByWithRelationInput!]) { + findManyActivities( orderBy: $orderBy - where: {commentThreadTargets: {some: {commentableId: {in: $commentThreadTargetIds}}}} + where: {activityTargets: {some: {commentableId: {in: $activityTargetIds}}}} ) { id createdAt @@ -2639,46 +2770,46 @@ export const GetCommentThreadsByTargetsDocument = gql` avatarUrl } } - commentThreadTargets { + activityTargets { id - commentableId commentableType + commentableId } } } `; /** - * __useGetCommentThreadsByTargetsQuery__ + * __useGetActivitiesByTargetsQuery__ * - * To run a query within a React component, call `useGetCommentThreadsByTargetsQuery` and pass it any options that fit your needs. - * When your component renders, `useGetCommentThreadsByTargetsQuery` returns an object from Apollo Client that contains loading, error, and data properties + * To run a query within a React component, call `useGetActivitiesByTargetsQuery` and pass it any options that fit your needs. + * When your component renders, `useGetActivitiesByTargetsQuery` returns an object from Apollo Client that contains loading, error, and data properties * you can use to render your UI. * * @param baseOptions options that will be passed into the query, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options; * * @example - * const { data, loading, error } = useGetCommentThreadsByTargetsQuery({ + * const { data, loading, error } = useGetActivitiesByTargetsQuery({ * variables: { - * commentThreadTargetIds: // value for 'commentThreadTargetIds' + * activityTargetIds: // value for 'activityTargetIds' * orderBy: // value for 'orderBy' * }, * }); */ -export function useGetCommentThreadsByTargetsQuery(baseOptions: Apollo.QueryHookOptions) { +export function useGetActivitiesByTargetsQuery(baseOptions: Apollo.QueryHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useQuery(GetCommentThreadsByTargetsDocument, options); + return Apollo.useQuery(GetActivitiesByTargetsDocument, options); } -export function useGetCommentThreadsByTargetsLazyQuery(baseOptions?: Apollo.LazyQueryHookOptions) { +export function useGetActivitiesByTargetsLazyQuery(baseOptions?: Apollo.LazyQueryHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useLazyQuery(GetCommentThreadsByTargetsDocument, options); + return Apollo.useLazyQuery(GetActivitiesByTargetsDocument, options); } -export type GetCommentThreadsByTargetsQueryHookResult = ReturnType; -export type GetCommentThreadsByTargetsLazyQueryHookResult = ReturnType; -export type GetCommentThreadsByTargetsQueryResult = Apollo.QueryResult; -export const GetCommentThreadDocument = gql` - query GetCommentThread($commentThreadId: String!) { - findManyCommentThreads(where: {id: {equals: $commentThreadId}}) { +export type GetActivitiesByTargetsQueryHookResult = ReturnType; +export type GetActivitiesByTargetsLazyQueryHookResult = ReturnType; +export type GetActivitiesByTargetsQueryResult = Apollo.QueryResult; +export const GetActivityDocument = gql` + query GetActivity($activityId: String!) { + findManyActivities(where: {id: {equals: $activityId}}) { id createdAt body @@ -2704,52 +2835,52 @@ export const GetCommentThreadDocument = gql` avatarUrl } } - commentThreadTargets { + activityTargets { id - commentableId commentableType + commentableId } } } `; /** - * __useGetCommentThreadQuery__ + * __useGetActivityQuery__ * - * To run a query within a React component, call `useGetCommentThreadQuery` and pass it any options that fit your needs. - * When your component renders, `useGetCommentThreadQuery` returns an object from Apollo Client that contains loading, error, and data properties + * To run a query within a React component, call `useGetActivityQuery` and pass it any options that fit your needs. + * When your component renders, `useGetActivityQuery` returns an object from Apollo Client that contains loading, error, and data properties * you can use to render your UI. * * @param baseOptions options that will be passed into the query, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options; * * @example - * const { data, loading, error } = useGetCommentThreadQuery({ + * const { data, loading, error } = useGetActivityQuery({ * variables: { - * commentThreadId: // value for 'commentThreadId' + * activityId: // value for 'activityId' * }, * }); */ -export function useGetCommentThreadQuery(baseOptions: Apollo.QueryHookOptions) { +export function useGetActivityQuery(baseOptions: Apollo.QueryHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useQuery(GetCommentThreadDocument, options); + return Apollo.useQuery(GetActivityDocument, options); } -export function useGetCommentThreadLazyQuery(baseOptions?: Apollo.LazyQueryHookOptions) { +export function useGetActivityLazyQuery(baseOptions?: Apollo.LazyQueryHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useLazyQuery(GetCommentThreadDocument, options); + return Apollo.useLazyQuery(GetActivityDocument, options); } -export type GetCommentThreadQueryHookResult = ReturnType; -export type GetCommentThreadLazyQueryHookResult = ReturnType; -export type GetCommentThreadQueryResult = Apollo.QueryResult; -export const AddCommentThreadTargetsOnCommentThreadDocument = gql` - mutation AddCommentThreadTargetsOnCommentThread($commentThreadId: String!, $commentThreadTargetInputs: [CommentThreadTargetCreateManyCommentThreadInput!]!) { - updateOneCommentThread( - where: {id: $commentThreadId} - data: {commentThreadTargets: {createMany: {data: $commentThreadTargetInputs}}} +export type GetActivityQueryHookResult = ReturnType; +export type GetActivityLazyQueryHookResult = ReturnType; +export type GetActivityQueryResult = Apollo.QueryResult; +export const AddActivityTargetsOnActivityDocument = gql` + mutation AddActivityTargetsOnActivity($activityId: String!, $activityTargetInputs: [ActivityTargetCreateManyActivityInput!]!) { + updateOneActivity( + where: {id: $activityId} + data: {activityTargets: {createMany: {data: $activityTargetInputs}}} ) { id createdAt updatedAt - commentThreadTargets { + activityTargets { id createdAt updatedAt @@ -2759,43 +2890,43 @@ export const AddCommentThreadTargetsOnCommentThreadDocument = gql` } } `; -export type AddCommentThreadTargetsOnCommentThreadMutationFn = Apollo.MutationFunction; +export type AddActivityTargetsOnActivityMutationFn = Apollo.MutationFunction; /** - * __useAddCommentThreadTargetsOnCommentThreadMutation__ + * __useAddActivityTargetsOnActivityMutation__ * - * To run a mutation, you first call `useAddCommentThreadTargetsOnCommentThreadMutation` within a React component and pass it any options that fit your needs. - * When your component renders, `useAddCommentThreadTargetsOnCommentThreadMutation` returns a tuple that includes: + * To run a mutation, you first call `useAddActivityTargetsOnActivityMutation` within a React component and pass it any options that fit your needs. + * When your component renders, `useAddActivityTargetsOnActivityMutation` returns a tuple that includes: * - A mutate function that you can call at any time to execute the mutation * - An object with fields that represent the current status of the mutation's execution * * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2; * * @example - * const [addCommentThreadTargetsOnCommentThreadMutation, { data, loading, error }] = useAddCommentThreadTargetsOnCommentThreadMutation({ + * const [addActivityTargetsOnActivityMutation, { data, loading, error }] = useAddActivityTargetsOnActivityMutation({ * variables: { - * commentThreadId: // value for 'commentThreadId' - * commentThreadTargetInputs: // value for 'commentThreadTargetInputs' + * activityId: // value for 'activityId' + * activityTargetInputs: // value for 'activityTargetInputs' * }, * }); */ -export function useAddCommentThreadTargetsOnCommentThreadMutation(baseOptions?: Apollo.MutationHookOptions) { +export function useAddActivityTargetsOnActivityMutation(baseOptions?: Apollo.MutationHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useMutation(AddCommentThreadTargetsOnCommentThreadDocument, options); + return Apollo.useMutation(AddActivityTargetsOnActivityDocument, options); } -export type AddCommentThreadTargetsOnCommentThreadMutationHookResult = ReturnType; -export type AddCommentThreadTargetsOnCommentThreadMutationResult = Apollo.MutationResult; -export type AddCommentThreadTargetsOnCommentThreadMutationOptions = Apollo.BaseMutationOptions; -export const RemoveCommentThreadTargetsOnCommentThreadDocument = gql` - mutation RemoveCommentThreadTargetsOnCommentThread($commentThreadId: String!, $commentThreadTargetIds: [String!]!) { - updateOneCommentThread( - where: {id: $commentThreadId} - data: {commentThreadTargets: {deleteMany: {id: {in: $commentThreadTargetIds}}}} +export type AddActivityTargetsOnActivityMutationHookResult = ReturnType; +export type AddActivityTargetsOnActivityMutationResult = Apollo.MutationResult; +export type AddActivityTargetsOnActivityMutationOptions = Apollo.BaseMutationOptions; +export const RemoveActivityTargetsOnActivityDocument = gql` + mutation RemoveActivityTargetsOnActivity($activityId: String!, $activityTargetIds: [String!]!) { + updateOneActivity( + where: {id: $activityId} + data: {activityTargets: {deleteMany: {id: {in: $activityTargetIds}}}} ) { id createdAt updatedAt - commentThreadTargets { + activityTargets { id createdAt updatedAt @@ -2805,69 +2936,69 @@ export const RemoveCommentThreadTargetsOnCommentThreadDocument = gql` } } `; -export type RemoveCommentThreadTargetsOnCommentThreadMutationFn = Apollo.MutationFunction; +export type RemoveActivityTargetsOnActivityMutationFn = Apollo.MutationFunction; /** - * __useRemoveCommentThreadTargetsOnCommentThreadMutation__ + * __useRemoveActivityTargetsOnActivityMutation__ * - * To run a mutation, you first call `useRemoveCommentThreadTargetsOnCommentThreadMutation` within a React component and pass it any options that fit your needs. - * When your component renders, `useRemoveCommentThreadTargetsOnCommentThreadMutation` returns a tuple that includes: + * To run a mutation, you first call `useRemoveActivityTargetsOnActivityMutation` within a React component and pass it any options that fit your needs. + * When your component renders, `useRemoveActivityTargetsOnActivityMutation` returns a tuple that includes: * - A mutate function that you can call at any time to execute the mutation * - An object with fields that represent the current status of the mutation's execution * * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2; * * @example - * const [removeCommentThreadTargetsOnCommentThreadMutation, { data, loading, error }] = useRemoveCommentThreadTargetsOnCommentThreadMutation({ + * const [removeActivityTargetsOnActivityMutation, { data, loading, error }] = useRemoveActivityTargetsOnActivityMutation({ * variables: { - * commentThreadId: // value for 'commentThreadId' - * commentThreadTargetIds: // value for 'commentThreadTargetIds' + * activityId: // value for 'activityId' + * activityTargetIds: // value for 'activityTargetIds' * }, * }); */ -export function useRemoveCommentThreadTargetsOnCommentThreadMutation(baseOptions?: Apollo.MutationHookOptions) { +export function useRemoveActivityTargetsOnActivityMutation(baseOptions?: Apollo.MutationHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useMutation(RemoveCommentThreadTargetsOnCommentThreadDocument, options); + return Apollo.useMutation(RemoveActivityTargetsOnActivityDocument, options); } -export type RemoveCommentThreadTargetsOnCommentThreadMutationHookResult = ReturnType; -export type RemoveCommentThreadTargetsOnCommentThreadMutationResult = Apollo.MutationResult; -export type RemoveCommentThreadTargetsOnCommentThreadMutationOptions = Apollo.BaseMutationOptions; -export const DeleteCommentThreadDocument = gql` - mutation DeleteCommentThread($commentThreadId: String!) { - deleteManyCommentThreads(where: {id: {equals: $commentThreadId}}) { +export type RemoveActivityTargetsOnActivityMutationHookResult = ReturnType; +export type RemoveActivityTargetsOnActivityMutationResult = Apollo.MutationResult; +export type RemoveActivityTargetsOnActivityMutationOptions = Apollo.BaseMutationOptions; +export const DeleteActivityDocument = gql` + mutation DeleteActivity($activityId: String!) { + deleteManyActivities(where: {id: {equals: $activityId}}) { count } } `; -export type DeleteCommentThreadMutationFn = Apollo.MutationFunction; +export type DeleteActivityMutationFn = Apollo.MutationFunction; /** - * __useDeleteCommentThreadMutation__ + * __useDeleteActivityMutation__ * - * To run a mutation, you first call `useDeleteCommentThreadMutation` within a React component and pass it any options that fit your needs. - * When your component renders, `useDeleteCommentThreadMutation` returns a tuple that includes: + * To run a mutation, you first call `useDeleteActivityMutation` within a React component and pass it any options that fit your needs. + * When your component renders, `useDeleteActivityMutation` returns a tuple that includes: * - A mutate function that you can call at any time to execute the mutation * - An object with fields that represent the current status of the mutation's execution * * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2; * * @example - * const [deleteCommentThreadMutation, { data, loading, error }] = useDeleteCommentThreadMutation({ + * const [deleteActivityMutation, { data, loading, error }] = useDeleteActivityMutation({ * variables: { - * commentThreadId: // value for 'commentThreadId' + * activityId: // value for 'activityId' * }, * }); */ -export function useDeleteCommentThreadMutation(baseOptions?: Apollo.MutationHookOptions) { +export function useDeleteActivityMutation(baseOptions?: Apollo.MutationHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useMutation(DeleteCommentThreadDocument, options); + return Apollo.useMutation(DeleteActivityDocument, options); } -export type DeleteCommentThreadMutationHookResult = ReturnType; -export type DeleteCommentThreadMutationResult = Apollo.MutationResult; -export type DeleteCommentThreadMutationOptions = Apollo.BaseMutationOptions; -export const UpdateCommentThreadDocument = gql` - mutation UpdateCommentThread($id: String!, $body: String, $title: String, $type: ActivityType, $completedAt: DateTime) { - updateOneCommentThread( +export type DeleteActivityMutationHookResult = ReturnType; +export type DeleteActivityMutationResult = Apollo.MutationResult; +export type DeleteActivityMutationOptions = Apollo.BaseMutationOptions; +export const UpdateActivityDocument = gql` + mutation UpdateActivity($id: String!, $body: String, $title: String, $type: ActivityType, $completedAt: DateTime) { + updateOneActivity( where: {id: $id} data: {body: $body, title: $title, type: $type, completedAt: $completedAt} ) { @@ -2879,20 +3010,20 @@ export const UpdateCommentThreadDocument = gql` } } `; -export type UpdateCommentThreadMutationFn = Apollo.MutationFunction; +export type UpdateActivityMutationFn = Apollo.MutationFunction; /** - * __useUpdateCommentThreadMutation__ + * __useUpdateActivityMutation__ * - * To run a mutation, you first call `useUpdateCommentThreadMutation` within a React component and pass it any options that fit your needs. - * When your component renders, `useUpdateCommentThreadMutation` returns a tuple that includes: + * To run a mutation, you first call `useUpdateActivityMutation` within a React component and pass it any options that fit your needs. + * When your component renders, `useUpdateActivityMutation` returns a tuple that includes: * - A mutate function that you can call at any time to execute the mutation * - An object with fields that represent the current status of the mutation's execution * * @param baseOptions options that will be passed into the mutation, supported options are listed on: https://www.apollographql.com/docs/react/api/react-hooks/#options-2; * * @example - * const [updateCommentThreadMutation, { data, loading, error }] = useUpdateCommentThreadMutation({ + * const [updateActivityMutation, { data, loading, error }] = useUpdateActivityMutation({ * variables: { * id: // value for 'id' * body: // value for 'body' @@ -2902,13 +3033,13 @@ export type UpdateCommentThreadMutationFn = Apollo.MutationFunction) { +export function useUpdateActivityMutation(baseOptions?: Apollo.MutationHookOptions) { const options = {...defaultOptions, ...baseOptions} - return Apollo.useMutation(UpdateCommentThreadDocument, options); + return Apollo.useMutation(UpdateActivityDocument, options); } -export type UpdateCommentThreadMutationHookResult = ReturnType; -export type UpdateCommentThreadMutationResult = Apollo.MutationResult; -export type UpdateCommentThreadMutationOptions = Apollo.BaseMutationOptions; +export type UpdateActivityMutationHookResult = ReturnType; +export type UpdateActivityMutationResult = Apollo.MutationResult; +export type UpdateActivityMutationOptions = Apollo.BaseMutationOptions; export const UploadAttachmentDocument = gql` mutation UploadAttachment($file: Upload!, $activityId: String!) { uploadAttachment(file: $file, activityId: $activityId) @@ -3248,7 +3379,7 @@ export const GetCompaniesDocument = gql` address linkedinUrl employees - _commentThreadCount + _activityCount accountOwner { id email @@ -3299,7 +3430,7 @@ export const GetCompanyDocument = gql` address linkedinUrl employees - _commentThreadCount + _activityCount accountOwner { id email @@ -3469,7 +3600,7 @@ export const GetPeopleDocument = gql` jobTitle linkedinUrl createdAt - _commentThreadCount + _activityCount company { id name @@ -3587,7 +3718,7 @@ export const GetPersonNamesAndCommentCountByIdDocument = gql` firstName lastName displayName - _commentThreadCount + _activityCount } } `; @@ -3663,7 +3794,7 @@ export const GetPersonCommentCountByIdDocument = gql` query GetPersonCommentCountById($id: String!) { person: findUniquePerson(id: $id) { id - _commentThreadCount + _activityCount } } `; @@ -3780,7 +3911,7 @@ export const GetPersonDocument = gql` jobTitle linkedinUrl phone - _commentThreadCount + _activityCount company { id name diff --git a/front/src/modules/activities/comment/__stories__/Comment.stories.tsx b/front/src/modules/activities/comment/__stories__/Comment.stories.tsx index aaf31f461..265a19a88 100644 --- a/front/src/modules/activities/comment/__stories__/Comment.stories.tsx +++ b/front/src/modules/activities/comment/__stories__/Comment.stories.tsx @@ -2,7 +2,7 @@ import type { Meta, StoryObj } from '@storybook/react'; import { ComponentDecorator } from '~/testing/decorators/ComponentDecorator'; -import { CommentThreadActionBar } from '../../right-drawer/components/CommentThreadActionBar'; +import { ActivityActionBar } from '../../right-drawer/components/ActivityActionBar'; import { Comment } from '../Comment'; import { mockComment, mockCommentWithLongValues } from './mock-comment'; @@ -15,7 +15,7 @@ const meta: Meta = { actionBar: { type: 'boolean', mapping: { - true: , + true: , false: undefined, }, }, diff --git a/front/src/modules/activities/comment/__stories__/CommentHeader.stories.tsx b/front/src/modules/activities/comment/__stories__/CommentHeader.stories.tsx index 3e5a53eb3..00def6aba 100644 --- a/front/src/modules/activities/comment/__stories__/CommentHeader.stories.tsx +++ b/front/src/modules/activities/comment/__stories__/CommentHeader.stories.tsx @@ -1,7 +1,7 @@ import type { Meta, StoryObj } from '@storybook/react'; import { DateTime } from 'luxon'; -import { CommentThreadActionBar } from '@/activities/right-drawer/components/CommentThreadActionBar'; +import { ActivityActionBar } from '@/activities/right-drawer/components/ActivityActionBar'; import { ComponentDecorator } from '~/testing/decorators/ComponentDecorator'; import { avatarUrl } from '~/testing/mock-data/users'; @@ -17,7 +17,7 @@ const meta: Meta = { actionBar: { type: 'boolean', mapping: { - true: , + true: , false: undefined, }, }, diff --git a/front/src/modules/activities/components/CommentThreadBodyEditor.tsx b/front/src/modules/activities/components/ActivityBodyEditor.tsx similarity index 55% rename from front/src/modules/activities/components/CommentThreadBodyEditor.tsx rename to front/src/modules/activities/components/ActivityBodyEditor.tsx index ddf4bad5c..721ef3830 100644 --- a/front/src/modules/activities/components/CommentThreadBodyEditor.tsx +++ b/front/src/modules/activities/components/ActivityBodyEditor.tsx @@ -6,24 +6,21 @@ import styled from '@emotion/styled'; import debounce from 'lodash.debounce'; import { BlockEditor } from '@/ui/editor/components/BlockEditor'; -import { - CommentThread, - useUpdateCommentThreadMutation, -} from '~/generated/graphql'; +import { Activity, useUpdateActivityMutation } from '~/generated/graphql'; -import { GET_COMMENT_THREADS_BY_TARGETS } from '../queries/select'; +import { GET_ACTIVITIES_BY_TARGETS } from '../queries/select'; const BlockNoteStyledContainer = styled.div` width: 100%; `; type OwnProps = { - commentThread: Pick; - onChange?: (commentThreadBody: string) => void; + activity: Pick; + onChange?: (activityBody: string) => void; }; -export function CommentThreadBodyEditor({ commentThread, onChange }: OwnProps) { - const [updateCommentThreadMutation] = useUpdateCommentThreadMutation(); +export function ActivityBodyEditor({ activity, onChange }: OwnProps) { + const [updateActivityMutation] = useUpdateActivityMutation(); const [body, setBody] = useState(null); @@ -34,26 +31,22 @@ export function CommentThreadBodyEditor({ commentThread, onChange }: OwnProps) { }, [body, onChange]); const debounceOnChange = useMemo(() => { - function onInternalChange(commentThreadBody: string) { - setBody(commentThreadBody); - updateCommentThreadMutation({ + function onInternalChange(activityBody: string) { + setBody(activityBody); + updateActivityMutation({ variables: { - id: commentThread.id, - body: commentThreadBody, + id: activity.id, + body: activityBody, }, - refetchQueries: [ - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', - ], + refetchQueries: [getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? ''], }); } return debounce(onInternalChange, 200); - }, [commentThread, updateCommentThreadMutation, setBody]); + }, [activity, updateActivityMutation, setBody]); const editor: BlockNoteEditor | null = useBlockNote({ - initialContent: commentThread.body - ? JSON.parse(commentThread.body) - : undefined, + initialContent: activity.body ? JSON.parse(activity.body) : undefined, editorDOMAttributes: { class: 'editor' }, onEditorContentChange: (editor) => { debounceOnChange(JSON.stringify(editor.topLevelBlocks) ?? ''); diff --git a/front/src/modules/activities/components/CommentThreadComments.tsx b/front/src/modules/activities/components/ActivityComments.tsx similarity index 84% rename from front/src/modules/activities/components/CommentThreadComments.tsx rename to front/src/modules/activities/components/ActivityComments.tsx index 363391b45..e4fbf4429 100644 --- a/front/src/modules/activities/components/CommentThreadComments.tsx +++ b/front/src/modules/activities/components/ActivityComments.tsx @@ -6,15 +6,15 @@ import { v4 } from 'uuid'; import { currentUserState } from '@/auth/states/currentUserState'; import { useIsMobile } from '@/ui/hooks/useIsMobile'; import { AutosizeTextInput } from '@/ui/input/components/AutosizeTextInput'; -import { CommentThread, useCreateCommentMutation } from '~/generated/graphql'; +import { Activity, useCreateCommentMutation } from '~/generated/graphql'; import { isNonEmptyString } from '~/utils/isNonEmptyString'; import { Comment } from '../comment/Comment'; -import { GET_COMMENT_THREAD } from '../queries'; +import { GET_ACTIVITY } from '../queries'; import { CommentForDrawer } from '../types/CommentForDrawer'; type OwnProps = { - commentThread: Pick & { + activity: Pick & { comments: Array; }; }; @@ -52,7 +52,7 @@ const StyledThreadCommentTitle = styled.div` text-transform: uppercase; `; -export function CommentThreadComments({ commentThread }: OwnProps) { +export function ActivityComments({ activity }: OwnProps) { const [createCommentMutation] = useCreateCommentMutation(); const currentUser = useRecoilValue(currentUserState); @@ -69,21 +69,21 @@ export function CommentThreadComments({ commentThread }: OwnProps) { variables: { commentId: v4(), authorId: currentUser?.id ?? '', - commentThreadId: commentThread?.id ?? '', + activityId: activity?.id ?? '', commentText: commentText, createdAt: new Date().toISOString(), }, - refetchQueries: [getOperationName(GET_COMMENT_THREAD) ?? ''], + refetchQueries: [getOperationName(GET_ACTIVITY) ?? ''], }); } return ( <> - {commentThread?.comments.length > 0 && ( + {activity?.comments.length > 0 && ( <> Comments - {commentThread?.comments?.map((comment) => ( + {activity?.comments?.map((comment) => ( ))} diff --git a/front/src/modules/activities/components/CommentThreadCreateButton.tsx b/front/src/modules/activities/components/ActivityCreateButton.tsx similarity index 88% rename from front/src/modules/activities/components/CommentThreadCreateButton.tsx rename to front/src/modules/activities/components/ActivityCreateButton.tsx index fb6315936..767d4be1d 100644 --- a/front/src/modules/activities/components/CommentThreadCreateButton.tsx +++ b/front/src/modules/activities/components/ActivityCreateButton.tsx @@ -4,17 +4,17 @@ import { Button, ButtonVariant } from '@/ui/button/components/Button'; import { ButtonGroup } from '@/ui/button/components/ButtonGroup'; import { IconCheckbox, IconNotes, IconTimelineEvent } from '@/ui/icon/index'; -type CommentThreadCreateButtonProps = { +type ActivityCreateButtonProps = { onNoteClick?: () => void; onTaskClick?: () => void; onActivityClick?: () => void; }; -export function CommentThreadCreateButton({ +export function ActivityCreateButton({ onNoteClick, onTaskClick, onActivityClick, -}: CommentThreadCreateButtonProps) { +}: ActivityCreateButtonProps) { const theme = useTheme(); return ( diff --git a/front/src/modules/activities/components/CommentThreadEditor.tsx b/front/src/modules/activities/components/ActivityEditor.tsx similarity index 61% rename from front/src/modules/activities/components/CommentThreadEditor.tsx rename to front/src/modules/activities/components/ActivityEditor.tsx index 92e6c7099..cda03ab93 100644 --- a/front/src/modules/activities/components/CommentThreadEditor.tsx +++ b/front/src/modules/activities/components/ActivityEditor.tsx @@ -2,26 +2,26 @@ import React, { useCallback, useState } from 'react'; import { getOperationName } from '@apollo/client/utilities'; import styled from '@emotion/styled'; -import { CommentThreadBodyEditor } from '@/activities/components/CommentThreadBodyEditor'; -import { CommentThreadComments } from '@/activities/components/CommentThreadComments'; -import { CommentThreadRelationPicker } from '@/activities/components/CommentThreadRelationPicker'; -import { CommentThreadTypeDropdown } from '@/activities/components/CommentThreadTypeDropdown'; -import { GET_COMMENT_THREADS_BY_TARGETS } from '@/activities/queries'; +import { ActivityBodyEditor } from '@/activities/components/ActivityBodyEditor'; +import { ActivityComments } from '@/activities/components/ActivityComments'; +import { ActivityRelationPicker } from '@/activities/components/ActivityRelationPicker'; +import { ActivityTypeDropdown } from '@/activities/components/ActivityTypeDropdown'; +import { GET_ACTIVITIES_BY_TARGETS } from '@/activities/queries'; import { PropertyBox } from '@/ui/editable-field/property-box/components/PropertyBox'; import { PropertyBoxItem } from '@/ui/editable-field/property-box/components/PropertyBoxItem'; import { useIsMobile } from '@/ui/hooks/useIsMobile'; import { IconArrowUpRight } from '@/ui/icon/index'; import { - CommentThread, - CommentThreadTarget, - useUpdateCommentThreadMutation, + Activity, + ActivityTarget, + useUpdateActivityMutation, } from '~/generated/graphql'; import { debounce } from '~/utils/debounce'; -import { CommentThreadActionBar } from '../right-drawer/components/CommentThreadActionBar'; +import { ActivityActionBar } from '../right-drawer/components/ActivityActionBar'; import { CommentForDrawer } from '../types/CommentForDrawer'; -import { CommentThreadTitle } from './CommentThreadTitle'; +import { ActivityTitle } from './ActivityTitle'; import '@blocknote/core/style.css'; @@ -65,64 +65,57 @@ const StyledTopActionsContainer = styled.div` `; type OwnProps = { - commentThread: Pick< - CommentThread, - 'id' | 'title' | 'body' | 'type' | 'completedAt' - > & { + activity: Pick & { comments?: Array | null; } & { - commentThreadTargets?: Array< - Pick + activityTargets?: Array< + Pick > | null; }; showComment?: boolean; autoFillTitle?: boolean; }; -export function CommentThreadEditor({ - commentThread, +export function ActivityEditor({ + activity, showComment = true, autoFillTitle = false, }: OwnProps) { const [hasUserManuallySetTitle, setHasUserManuallySetTitle] = useState(false); - const [title, setTitle] = useState(commentThread.title ?? ''); + const [title, setTitle] = useState(activity.title ?? ''); const [completedAt, setCompletedAt] = useState( - commentThread.completedAt ?? '', + activity.completedAt ?? '', ); - const [updateCommentThreadMutation] = useUpdateCommentThreadMutation(); + const [updateActivityMutation] = useUpdateActivityMutation(); const updateTitle = useCallback( (newTitle: string) => { - updateCommentThreadMutation({ + updateActivityMutation({ variables: { - id: commentThread.id, + id: activity.id, title: newTitle ?? '', }, - refetchQueries: [ - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', - ], + refetchQueries: [getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? ''], }); }, - [commentThread, updateCommentThreadMutation], + [activity, updateActivityMutation], ); const handleActivityCompletionChange = useCallback( (value: boolean) => { - updateCommentThreadMutation({ + updateActivityMutation({ variables: { - id: commentThread.id, + id: activity.id, completedAt: value ? new Date().toISOString() : null, }, - refetchQueries: [ - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', - ], + refetchQueries: [getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? ''], }); setCompletedAt(value ? new Date().toISOString() : null); }, - [commentThread, updateCommentThreadMutation], + [activity, updateActivityMutation], ); const debouncedUpdateTitle = debounce(updateTitle, 200); @@ -135,7 +128,7 @@ export function CommentThreadEditor({ } } - if (!commentThread) { + if (!activity) { return <>; } @@ -144,13 +137,13 @@ export function CommentThreadEditor({ - - + + - { setTitle(newTitle); setHasUserManuallySetTitle(true); @@ -162,11 +155,10 @@ export function CommentThreadEditor({ } value={ - } @@ -174,16 +166,16 @@ export function CommentThreadEditor({ /> - {showComment && ( - )} diff --git a/front/src/modules/activities/components/CommentThreadRelationPicker.tsx b/front/src/modules/activities/components/ActivityRelationPicker.tsx similarity index 90% rename from front/src/modules/activities/components/CommentThreadRelationPicker.tsx rename to front/src/modules/activities/components/ActivityRelationPicker.tsx index dff9c41c5..ec16d9357 100644 --- a/front/src/modules/activities/components/CommentThreadRelationPicker.tsx +++ b/front/src/modules/activities/components/ActivityRelationPicker.tsx @@ -18,19 +18,15 @@ import { useScopedHotkeys } from '@/ui/hotkey/hooks/useScopedHotkeys'; import { RecoilScope } from '@/ui/recoil-scope/components/RecoilScope'; import { MultipleEntitySelect } from '@/ui/relation-picker/components/MultipleEntitySelect'; import { RelationPickerHotkeyScope } from '@/ui/relation-picker/types/RelationPickerHotkeyScope'; -import { - CommentableType, - CommentThread, - CommentThreadTarget, -} from '~/generated/graphql'; +import { Activity, ActivityTarget, CommentableType } from '~/generated/graphql'; -import { useHandleCheckableCommentThreadTargetChange } from '../hooks/useHandleCheckableCommentThreadTargetChange'; +import { useHandleCheckableActivityTargetChange } from '../hooks/useHandleCheckableActivityTargetChange'; import { flatMapAndSortEntityForSelectArrayOfArrayByName } from '../utils/flatMapAndSortEntityForSelectArrayByName'; type OwnProps = { - commentThread?: Pick & { - commentThreadTargets: Array< - Pick + activity?: Pick & { + activityTargets: Array< + Pick >; }; }; @@ -75,7 +71,7 @@ const StyledMenuWrapper = styled.div` z-index: ${({ theme }) => theme.lastLayerZIndex}; `; -export function CommentThreadRelationPicker({ commentThread }: OwnProps) { +export function ActivityRelationPicker({ activity }: OwnProps) { const [isMenuOpen, setIsMenuOpen] = useState(false); const [searchFilter, setSearchFilter] = useState(''); const [selectedEntityIds, setSelectedEntityIds] = useState< @@ -88,17 +84,18 @@ export function CommentThreadRelationPicker({ commentThread }: OwnProps) { const initialPeopleIds = useMemo( () => - commentThread?.commentThreadTargets + activity?.activityTargets ?.filter((relation) => relation.commentableType === 'Person') .map((relation) => relation.commentableId) ?? [], - [commentThread?.commentThreadTargets], + [activity?.activityTargets], ); + const initialCompanyIds = useMemo( () => - commentThread?.commentThreadTargets + activity?.activityTargets ?.filter((relation) => relation.commentableType === 'Company') .map((relation) => relation.commentableId) ?? [], - [commentThread?.commentThreadTargets], + [activity?.activityTargets], ); const initialSelectedEntityIds = useMemo( @@ -135,8 +132,8 @@ export function CommentThreadRelationPicker({ commentThread }: OwnProps) { companiesForMultiSelect.entitiesToSelect, ]); - const handleCheckItemsChange = useHandleCheckableCommentThreadTargetChange({ - commentThread, + const handleCheckItemsChange = useHandleCheckableActivityTargetChange({ + activity, }); const exitEditMode = useCallback(() => { diff --git a/front/src/modules/activities/components/CommentThreadTitle.tsx b/front/src/modules/activities/components/ActivityTitle.tsx similarity index 98% rename from front/src/modules/activities/components/CommentThreadTitle.tsx rename to front/src/modules/activities/components/ActivityTitle.tsx index f6c707a4b..6634b50e5 100644 --- a/front/src/modules/activities/components/CommentThreadTitle.tsx +++ b/front/src/modules/activities/components/ActivityTitle.tsx @@ -51,7 +51,7 @@ type OwnProps = { onCompletionChange: (value: boolean) => void; }; -export function CommentThreadTitle({ +export function ActivityTitle({ title, completed, type, diff --git a/front/src/modules/activities/components/CommentThreadTypeDropdown.tsx b/front/src/modules/activities/components/ActivityTypeDropdown.tsx similarity index 67% rename from front/src/modules/activities/components/CommentThreadTypeDropdown.tsx rename to front/src/modules/activities/components/ActivityTypeDropdown.tsx index eef0771b7..c35c6cb35 100644 --- a/front/src/modules/activities/components/CommentThreadTypeDropdown.tsx +++ b/front/src/modules/activities/components/ActivityTypeDropdown.tsx @@ -7,17 +7,17 @@ import { ChipVariant, } from '@/ui/chip/components/Chip'; import { IconPhone } from '@/ui/icon'; -import { CommentThread } from '~/generated/graphql'; +import { Activity } from '~/generated/graphql'; type OwnProps = { - commentThread: Pick; + activity: Pick; }; -export function CommentThreadTypeDropdown({ commentThread }: OwnProps) { +export function ActivityTypeDropdown({ activity }: OwnProps) { const theme = useTheme(); return ( } size={ChipSize.Large} accent={ChipAccent.TextSecondary} diff --git a/front/src/modules/activities/components/__stories__/CommentThreadRelationPicker.stories.tsx b/front/src/modules/activities/components/__stories__/ActivityRelationPicker.stories.tsx similarity index 59% rename from front/src/modules/activities/components/__stories__/CommentThreadRelationPicker.stories.tsx rename to front/src/modules/activities/components/__stories__/ActivityRelationPicker.stories.tsx index e3c57cb15..e8ca2dcd0 100644 --- a/front/src/modules/activities/components/__stories__/CommentThreadRelationPicker.stories.tsx +++ b/front/src/modules/activities/components/__stories__/ActivityRelationPicker.stories.tsx @@ -4,17 +4,17 @@ import type { Meta, StoryObj } from '@storybook/react'; import { ComponentDecorator } from '~/testing/decorators/ComponentDecorator'; import { graphqlMocks } from '~/testing/graphqlMocks'; -import { mockedCommentThreads } from '~/testing/mock-data/comment-threads'; +import { mockedActivities } from '~/testing/mock-data/activities'; -import { CommentThreadRelationPicker } from '../CommentThreadRelationPicker'; +import { ActivityRelationPicker } from '../ActivityRelationPicker'; const StyledContainer = styled.div` width: 400px; `; -const meta: Meta = { - title: 'Modules/Comments/CommentThreadRelationPicker', - component: CommentThreadRelationPicker, +const meta: Meta = { + title: 'Modules/Comments/ActivityRelationPicker', + component: ActivityRelationPicker, decorators: [ (Story) => ( @@ -25,13 +25,13 @@ const meta: Meta = { ), ComponentDecorator, ], - args: { commentThread: mockedCommentThreads[0] }, + args: { activity: mockedActivities[0] }, parameters: { msw: graphqlMocks, }, }; export default meta; -type Story = StoryObj; +type Story = StoryObj; export const Default: Story = {}; diff --git a/front/src/modules/activities/hooks/useHandleCheckableActivityTargetChange.ts b/front/src/modules/activities/hooks/useHandleCheckableActivityTargetChange.ts new file mode 100644 index 000000000..841464246 --- /dev/null +++ b/front/src/modules/activities/hooks/useHandleCheckableActivityTargetChange.ts @@ -0,0 +1,84 @@ +import { getOperationName } from '@apollo/client/utilities'; +import { v4 } from 'uuid'; + +import { GET_COMPANIES } from '@/companies/queries'; +import { GET_PEOPLE } from '@/people/queries'; +import { + Activity, + ActivityTarget, + useAddActivityTargetsOnActivityMutation, + useRemoveActivityTargetsOnActivityMutation, +} from '~/generated/graphql'; + +import { GET_ACTIVITIES_BY_TARGETS } from '../queries'; +import { CommentableEntityForSelect } from '../types/CommentableEntityForSelect'; + +export function useHandleCheckableActivityTargetChange({ + activity, +}: { + activity?: Pick & { + activityTargets: Array< + Pick + >; + }; +}) { + const [addActivityTargetsOnActivity] = + useAddActivityTargetsOnActivityMutation({ + refetchQueries: [ + getOperationName(GET_COMPANIES) ?? '', + getOperationName(GET_PEOPLE) ?? '', + getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? '', + ], + }); + + const [removeActivityTargetsOnActivity] = + useRemoveActivityTargetsOnActivityMutation({ + refetchQueries: [ + getOperationName(GET_COMPANIES) ?? '', + getOperationName(GET_PEOPLE) ?? '', + getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? '', + ], + }); + + return async function handleCheckItemsChange( + entityValues: Record, + entities: CommentableEntityForSelect[], + ) { + if (!activity) { + return; + } + + const currentEntityIds = activity.activityTargets.map( + ({ commentableId }) => commentableId, + ); + + const entitiesToAdd = entities.filter( + ({ id }) => entityValues[id] && !currentEntityIds.includes(id), + ); + + if (entitiesToAdd.length) + await addActivityTargetsOnActivity({ + variables: { + activityId: activity.id, + activityTargetInputs: entitiesToAdd.map((entity) => ({ + id: v4(), + createdAt: new Date().toISOString(), + commentableType: entity.entityType, + commentableId: entity.id, + })), + }, + }); + + const activityTargetIdsToDelete = activity.activityTargets + .filter(({ commentableId }) => !entityValues[commentableId]) + .map(({ id }) => id); + + if (activityTargetIdsToDelete.length) + await removeActivityTargetsOnActivity({ + variables: { + activityId: activity.id, + activityTargetIds: activityTargetIdsToDelete, + }, + }); + }; +} diff --git a/front/src/modules/activities/hooks/useHandleCheckableCommentThreadTargetChange.ts b/front/src/modules/activities/hooks/useHandleCheckableCommentThreadTargetChange.ts deleted file mode 100644 index 388477da4..000000000 --- a/front/src/modules/activities/hooks/useHandleCheckableCommentThreadTargetChange.ts +++ /dev/null @@ -1,84 +0,0 @@ -import { getOperationName } from '@apollo/client/utilities'; -import { v4 } from 'uuid'; - -import { GET_COMPANIES } from '@/companies/queries'; -import { GET_PEOPLE } from '@/people/queries'; -import { - CommentThread, - CommentThreadTarget, - useAddCommentThreadTargetsOnCommentThreadMutation, - useRemoveCommentThreadTargetsOnCommentThreadMutation, -} from '~/generated/graphql'; - -import { GET_COMMENT_THREADS_BY_TARGETS } from '../queries'; -import { CommentableEntityForSelect } from '../types/CommentableEntityForSelect'; - -export function useHandleCheckableCommentThreadTargetChange({ - commentThread, -}: { - commentThread?: Pick & { - commentThreadTargets: Array< - Pick - >; - }; -}) { - const [addCommentThreadTargetsOnCommentThread] = - useAddCommentThreadTargetsOnCommentThreadMutation({ - refetchQueries: [ - getOperationName(GET_COMPANIES) ?? '', - getOperationName(GET_PEOPLE) ?? '', - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', - ], - }); - - const [removeCommentThreadTargetsOnCommentThread] = - useRemoveCommentThreadTargetsOnCommentThreadMutation({ - refetchQueries: [ - getOperationName(GET_COMPANIES) ?? '', - getOperationName(GET_PEOPLE) ?? '', - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', - ], - }); - - return async function handleCheckItemsChange( - entityValues: Record, - entities: CommentableEntityForSelect[], - ) { - if (!commentThread) { - return; - } - - const currentEntityIds = commentThread.commentThreadTargets.map( - ({ commentableId }) => commentableId, - ); - - const entitiesToAdd = entities.filter( - ({ id }) => entityValues[id] && !currentEntityIds.includes(id), - ); - - if (entitiesToAdd.length) - await addCommentThreadTargetsOnCommentThread({ - variables: { - commentThreadId: commentThread.id, - commentThreadTargetInputs: entitiesToAdd.map((entity) => ({ - id: v4(), - createdAt: new Date().toISOString(), - commentableType: entity.entityType, - commentableId: entity.id, - })), - }, - }); - - const commentThreadTargetIdsToDelete = commentThread.commentThreadTargets - .filter(({ commentableId }) => !entityValues[commentableId]) - .map(({ id }) => id); - - if (commentThreadTargetIdsToDelete.length) - await removeCommentThreadTargetsOnCommentThread({ - variables: { - commentThreadId: commentThread.id, - commentThreadTargetIds: commentThreadTargetIdsToDelete, - }, - }); - }; -} diff --git a/front/src/modules/activities/hooks/useOpenCommentThreadRightDrawer.ts b/front/src/modules/activities/hooks/useOpenActivityRightDrawer.ts similarity index 56% rename from front/src/modules/activities/hooks/useOpenCommentThreadRightDrawer.ts rename to front/src/modules/activities/hooks/useOpenActivityRightDrawer.ts index e678e9cc6..8a9d0e0ee 100644 --- a/front/src/modules/activities/hooks/useOpenCommentThreadRightDrawer.ts +++ b/front/src/modules/activities/hooks/useOpenActivityRightDrawer.ts @@ -5,18 +5,16 @@ import { useRightDrawer } from '@/ui/right-drawer/hooks/useRightDrawer'; import { RightDrawerHotkeyScope } from '@/ui/right-drawer/types/RightDrawerHotkeyScope'; import { RightDrawerPages } from '@/ui/right-drawer/types/RightDrawerPages'; -import { viewableCommentThreadIdState } from '../states/viewableCommentThreadIdState'; +import { viewableActivityIdState } from '../states/viewableActivityIdState'; -export function useOpenCommentThreadRightDrawer() { +export function useOpenActivityRightDrawer() { const { openRightDrawer } = useRightDrawer(); - const [, setViewableCommentThreadId] = useRecoilState( - viewableCommentThreadIdState, - ); + const [, setViewableActivityId] = useRecoilState(viewableActivityIdState); const setHotkeyScope = useSetHotkeyScope(); - return function openCommentThreadRightDrawer(commentThreadId: string) { + return function openActivityRightDrawer(activityId: string) { setHotkeyScope(RightDrawerHotkeyScope.RightDrawer, { goto: false }); - setViewableCommentThreadId(commentThreadId); - openRightDrawer(RightDrawerPages.EditCommentThread); + setViewableActivityId(activityId); + openRightDrawer(RightDrawerPages.EditActivity); }; } diff --git a/front/src/modules/activities/hooks/useOpenCreateCommentThreadDrawer.ts b/front/src/modules/activities/hooks/useOpenCreateActivityDrawer.ts similarity index 65% rename from front/src/modules/activities/hooks/useOpenCreateCommentThreadDrawer.ts rename to front/src/modules/activities/hooks/useOpenCreateActivityDrawer.ts index 45885bcb1..e913ce136 100644 --- a/front/src/modules/activities/hooks/useOpenCreateCommentThreadDrawer.ts +++ b/front/src/modules/activities/hooks/useOpenCreateActivityDrawer.ts @@ -9,40 +9,35 @@ import { useSetHotkeyScope } from '@/ui/hotkey/hooks/useSetHotkeyScope'; import { useRightDrawer } from '@/ui/right-drawer/hooks/useRightDrawer'; import { RightDrawerHotkeyScope } from '@/ui/right-drawer/types/RightDrawerHotkeyScope'; import { RightDrawerPages } from '@/ui/right-drawer/types/RightDrawerPages'; -import { - ActivityType, - useCreateCommentThreadMutation, -} from '~/generated/graphql'; +import { ActivityType, useCreateActivityMutation } from '~/generated/graphql'; -import { GET_COMMENT_THREAD, GET_COMMENT_THREADS_BY_TARGETS } from '../queries'; +import { GET_ACTIVITIES_BY_TARGETS, GET_ACTIVITY } from '../queries'; import { commentableEntityArrayState } from '../states/commentableEntityArrayState'; -import { viewableCommentThreadIdState } from '../states/viewableCommentThreadIdState'; +import { viewableActivityIdState } from '../states/viewableActivityIdState'; import { CommentableEntity } from '../types/CommentableEntity'; -export function useOpenCreateCommentThreadDrawer() { +export function useOpenCreateActivityDrawer() { const { openRightDrawer } = useRightDrawer(); - const [createCommentThreadMutation] = useCreateCommentThreadMutation(); + const [createActivityMutation] = useCreateActivityMutation(); const currentUser = useRecoilValue(currentUserState); const setHotkeyScope = useSetHotkeyScope(); const [, setCommentableEntityArray] = useRecoilState( commentableEntityArrayState, ); - const [, setViewableCommentThreadId] = useRecoilState( - viewableCommentThreadIdState, - ); + const [, setViewableActivityId] = useRecoilState(viewableActivityIdState); - return function openCreateCommentThreadDrawer( + return function openCreateActivityDrawer( entity: CommentableEntity, type: ActivityType, ) { - createCommentThreadMutation({ + createActivityMutation({ variables: { authorId: currentUser?.id ?? '', - commentThreadId: v4(), + activityId: v4(), createdAt: new Date().toISOString(), type: type, - commentThreadTargetArray: [ + activityTargetArray: [ { commentableId: entity.id, commentableType: entity.type, @@ -54,14 +49,14 @@ export function useOpenCreateCommentThreadDrawer() { refetchQueries: [ getOperationName(GET_COMPANIES) ?? '', getOperationName(GET_PEOPLE) ?? '', - getOperationName(GET_COMMENT_THREAD) ?? '', - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', + getOperationName(GET_ACTIVITY) ?? '', + getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? '', ], onCompleted(data) { setHotkeyScope(RightDrawerHotkeyScope.RightDrawer, { goto: false }); - setViewableCommentThreadId(data.createOneCommentThread.id); + setViewableActivityId(data.createOneActivity.id); setCommentableEntityArray([entity]); - openRightDrawer(RightDrawerPages.CreateCommentThread); + openRightDrawer(RightDrawerPages.CreateActivity); }, }); }; diff --git a/front/src/modules/activities/hooks/useOpenCreateCommentDrawerForSelectedRowIds.ts b/front/src/modules/activities/hooks/useOpenCreateActivityDrawerForSelectedRowIds.ts similarity index 71% rename from front/src/modules/activities/hooks/useOpenCreateCommentDrawerForSelectedRowIds.ts rename to front/src/modules/activities/hooks/useOpenCreateActivityDrawerForSelectedRowIds.ts index a81c50493..763edf211 100644 --- a/front/src/modules/activities/hooks/useOpenCreateCommentDrawerForSelectedRowIds.ts +++ b/front/src/modules/activities/hooks/useOpenCreateActivityDrawerForSelectedRowIds.ts @@ -13,21 +13,19 @@ import { selectedRowIdsSelector } from '@/ui/table/states/selectedRowIdsSelector import { ActivityType, CommentableType, - useCreateCommentThreadMutation, + useCreateActivityMutation, } from '~/generated/graphql'; -import { GET_COMMENT_THREAD, GET_COMMENT_THREADS_BY_TARGETS } from '../queries'; +import { GET_ACTIVITIES_BY_TARGETS, GET_ACTIVITY } from '../queries'; import { commentableEntityArrayState } from '../states/commentableEntityArrayState'; -import { viewableCommentThreadIdState } from '../states/viewableCommentThreadIdState'; +import { viewableActivityIdState } from '../states/viewableActivityIdState'; import { CommentableEntity } from '../types/CommentableEntity'; -export function useOpenCreateCommentThreadDrawerForSelectedRowIds() { +export function useOpenCreateActivityDrawerForSelectedRowIds() { const { openRightDrawer } = useRightDrawer(); - const [createCommentThreadMutation] = useCreateCommentThreadMutation(); + const [createActivityMutation] = useCreateActivityMutation(); const currentUser = useRecoilValue(currentUserState); - const [, setViewableCommentThreadId] = useRecoilState( - viewableCommentThreadIdState, - ); + const [, setViewableActivityId] = useRecoilState(viewableActivityIdState); const setHotkeyScope = useSetHotkeyScope(); @@ -47,13 +45,13 @@ export function useOpenCreateCommentThreadDrawerForSelectedRowIds() { }), ); - createCommentThreadMutation({ + createActivityMutation({ variables: { authorId: currentUser?.id ?? '', - commentThreadId: v4(), + activityId: v4(), createdAt: new Date().toISOString(), type: ActivityType.Note, - commentThreadTargetArray: commentableEntityArray.map((entity) => ({ + activityTargetArray: commentableEntityArray.map((entity) => ({ commentableId: entity.id, commentableType: entity.type, id: v4(), @@ -63,14 +61,14 @@ export function useOpenCreateCommentThreadDrawerForSelectedRowIds() { refetchQueries: [ getOperationName(GET_COMPANIES) ?? '', getOperationName(GET_PEOPLE) ?? '', - getOperationName(GET_COMMENT_THREAD) ?? '', - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', + getOperationName(GET_ACTIVITY) ?? '', + getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? '', ], onCompleted(data) { setHotkeyScope(RightDrawerHotkeyScope.RightDrawer, { goto: false }); - setViewableCommentThreadId(data.createOneCommentThread.id); + setViewableActivityId(data.createOneActivity.id); setCommentableEntityArray(commentableEntityArray); - openRightDrawer(RightDrawerPages.CreateCommentThread); + openRightDrawer(RightDrawerPages.CreateActivity); }, }); }; diff --git a/front/src/modules/activities/queries/create.ts b/front/src/modules/activities/queries/create.ts index 553eb667b..f7c3aea37 100644 --- a/front/src/modules/activities/queries/create.ts +++ b/front/src/modules/activities/queries/create.ts @@ -5,7 +5,7 @@ export const CREATE_COMMENT = gql` $commentId: String! $commentText: String! $authorId: String! - $commentThreadId: String! + $activityId: String! $createdAt: DateTime! ) { createOneComment( @@ -14,7 +14,7 @@ export const CREATE_COMMENT = gql` createdAt: $createdAt body: $commentText author: { connect: { id: $authorId } } - commentThread: { connect: { id: $commentThreadId } } + activity: { connect: { id: $activityId } } } ) { id @@ -27,32 +27,32 @@ export const CREATE_COMMENT = gql` lastName avatarUrl } - commentThreadId + activityId } } `; -export const CREATE_COMMENT_THREAD_WITH_COMMENT = gql` - mutation CreateCommentThread( - $commentThreadId: String! +export const CREATE_ACTIVITY_WITH_COMMENT = gql` + mutation CreateActivity( + $activityId: String! $body: String $title: String $type: ActivityType! $authorId: String! $createdAt: DateTime! - $commentThreadTargetArray: [CommentThreadTargetCreateManyCommentThreadInput!]! + $activityTargetArray: [ActivityTargetCreateManyActivityInput!]! ) { - createOneCommentThread( + createOneActivity( data: { - id: $commentThreadId + id: $activityId createdAt: $createdAt updatedAt: $createdAt author: { connect: { id: $authorId } } body: $body title: $title type: $type - commentThreadTargets: { - createMany: { data: $commentThreadTargetArray, skipDuplicates: true } + activityTargets: { + createMany: { data: $activityTargetArray, skipDuplicates: true } } } ) { @@ -61,11 +61,11 @@ export const CREATE_COMMENT_THREAD_WITH_COMMENT = gql` updatedAt authorId type - commentThreadTargets { + activityTargets { id createdAt updatedAt - commentThreadId + activityId commentableType commentableId } diff --git a/front/src/modules/activities/queries/select.ts b/front/src/modules/activities/queries/select.ts index 914b81623..6b9ec15c3 100644 --- a/front/src/modules/activities/queries/select.ts +++ b/front/src/modules/activities/queries/select.ts @@ -1,16 +1,14 @@ import { gql } from '@apollo/client'; -export const GET_COMMENT_THREADS_BY_TARGETS = gql` - query GetCommentThreadsByTargets( - $commentThreadTargetIds: [String!]! - $orderBy: [CommentThreadOrderByWithRelationInput!] +export const GET_ACTIVITIES_BY_TARGETS = gql` + query GetActivitiesByTargets( + $activityTargetIds: [String!]! + $orderBy: [ActivityOrderByWithRelationInput!] ) { - findManyCommentThreads( + findManyActivities( orderBy: $orderBy where: { - commentThreadTargets: { - some: { commentableId: { in: $commentThreadTargetIds } } - } + activityTargets: { some: { commentableId: { in: $activityTargetIds } } } } ) { id @@ -38,18 +36,18 @@ export const GET_COMMENT_THREADS_BY_TARGETS = gql` avatarUrl } } - commentThreadTargets { + activityTargets { id - commentableId commentableType + commentableId } } } `; -export const GET_COMMENT_THREAD = gql` - query GetCommentThread($commentThreadId: String!) { - findManyCommentThreads(where: { id: { equals: $commentThreadId } }) { +export const GET_ACTIVITY = gql` + query GetActivity($activityId: String!) { + findManyActivities(where: { id: { equals: $activityId } }) { id createdAt body @@ -75,10 +73,10 @@ export const GET_COMMENT_THREAD = gql` avatarUrl } } - commentThreadTargets { + activityTargets { id - commentableId commentableType + commentableId } } } diff --git a/front/src/modules/activities/queries/update.ts b/front/src/modules/activities/queries/update.ts index e28a66f6d..627ba1a3f 100644 --- a/front/src/modules/activities/queries/update.ts +++ b/front/src/modules/activities/queries/update.ts @@ -1,22 +1,18 @@ import { gql } from '@apollo/client'; -export const ADD_COMMENT_THREAD_TARGETS = gql` - mutation AddCommentThreadTargetsOnCommentThread( - $commentThreadId: String! - $commentThreadTargetInputs: [CommentThreadTargetCreateManyCommentThreadInput!]! +export const ADD_ACTIVITY_TARGETS = gql` + mutation AddActivityTargetsOnActivity( + $activityId: String! + $activityTargetInputs: [ActivityTargetCreateManyActivityInput!]! ) { - updateOneCommentThread( - where: { id: $commentThreadId } - data: { - commentThreadTargets: { - createMany: { data: $commentThreadTargetInputs } - } - } + updateOneActivity( + where: { id: $activityId } + data: { activityTargets: { createMany: { data: $activityTargetInputs } } } ) { id createdAt updatedAt - commentThreadTargets { + activityTargets { id createdAt updatedAt @@ -27,23 +23,21 @@ export const ADD_COMMENT_THREAD_TARGETS = gql` } `; -export const REMOVE_COMMENT_THREAD_TARGETS = gql` - mutation RemoveCommentThreadTargetsOnCommentThread( - $commentThreadId: String! - $commentThreadTargetIds: [String!]! +export const REMOVE_ACTIVITY_TARGETS = gql` + mutation RemoveActivityTargetsOnActivity( + $activityId: String! + $activityTargetIds: [String!]! ) { - updateOneCommentThread( - where: { id: $commentThreadId } + updateOneActivity( + where: { id: $activityId } data: { - commentThreadTargets: { - deleteMany: { id: { in: $commentThreadTargetIds } } - } + activityTargets: { deleteMany: { id: { in: $activityTargetIds } } } } ) { id createdAt updatedAt - commentThreadTargets { + activityTargets { id createdAt updatedAt @@ -54,23 +48,23 @@ export const REMOVE_COMMENT_THREAD_TARGETS = gql` } `; -export const DELETE_COMMENT_THREAD = gql` - mutation DeleteCommentThread($commentThreadId: String!) { - deleteManyCommentThreads(where: { id: { equals: $commentThreadId } }) { +export const DELETE_ACTIVITY = gql` + mutation DeleteActivity($activityId: String!) { + deleteManyActivities(where: { id: { equals: $activityId } }) { count } } `; -export const UPDATE_COMMENT_THREAD = gql` - mutation UpdateCommentThread( +export const UPDATE_ACTIVITY = gql` + mutation UpdateActivity( $id: String! $body: String $title: String $type: ActivityType $completedAt: DateTime ) { - updateOneCommentThread( + updateOneActivity( where: { id: $id } data: { body: $body diff --git a/front/src/modules/activities/right-drawer/components/Activity.tsx b/front/src/modules/activities/right-drawer/components/Activity.tsx new file mode 100644 index 000000000..b06c52f45 --- /dev/null +++ b/front/src/modules/activities/right-drawer/components/Activity.tsx @@ -0,0 +1,201 @@ +import React, { useEffect, useMemo, useState } from 'react'; +import { getOperationName } from '@apollo/client/utilities'; +import styled from '@emotion/styled'; + +import { ActivityBodyEditor } from '@/activities/components/ActivityBodyEditor'; +import { ActivityComments } from '@/activities/components/ActivityComments'; +import { ActivityRelationPicker } from '@/activities/components/ActivityRelationPicker'; +import { ActivityTypeDropdown } from '@/activities/components/ActivityTypeDropdown'; +import { GET_ACTIVITY } from '@/activities/queries'; +import { PropertyBox } from '@/ui/editable-field/property-box/components/PropertyBox'; +import { PropertyBoxItem } from '@/ui/editable-field/property-box/components/PropertyBoxItem'; +import { useIsMobile } from '@/ui/hooks/useIsMobile'; +import { IconArrowUpRight } from '@/ui/icon/index'; +import { + useGetActivityQuery, + useUpdateActivityMutation, +} from '~/generated/graphql'; +import { debounce } from '~/utils/debounce'; + +import { ActivityActionBar } from './ActivityActionBar'; + +import '@blocknote/core/style.css'; + +const StyledContainer = styled.div` + box-sizing: border-box; + display: flex; + flex-direction: column; + height: 100%; + justify-content: space-between; + overflow-y: auto; +`; + +const StyledUpperPartContainer = styled.div` + align-items: flex-start; + box-sizing: border-box; + display: flex; + flex-direction: column; + + gap: ${({ theme }) => theme.spacing(4)}; + justify-content: flex-start; +`; + +const StyledTopContainer = styled.div` + align-items: flex-start; + align-self: stretch; + background: ${({ theme }) => theme.background.secondary}; + border-bottom: ${({ theme }) => + useIsMobile() ? 'none' : `1px solid ${theme.border.color.medium}`}; + display: flex; + flex-direction: column; + gap: 24px; + padding: 24px 24px 24px 48px; +`; + +const StyledEditableTitleInput = styled.input` + background: transparent; + + border: none; + color: ${({ theme }) => theme.font.color.primary}; + display: flex; + flex: 1 0 0; + + flex-direction: column; + font-family: Inter; + font-size: ${({ theme }) => theme.font.size.xl}; + font-style: normal; + font-weight: ${({ theme }) => theme.font.weight.semiBold}; + justify-content: center; + + line-height: ${({ theme }) => theme.text.lineHeight.md}; + outline: none; + width: calc(100% - ${({ theme }) => theme.spacing(2)}); + &::placeholder { + color: ${({ theme }) => theme.font.color.light}; + } +`; + +const StyledTopActionsContainer = styled.div` + align-items: center; + display: flex; + flex-direction: row; + justify-content: space-between; + width: 100%; +`; + +type OwnProps = { + activityId: string; + showComment?: boolean; + autoFillTitle?: boolean; +}; + +export function Activity({ + activityId, + showComment = true, + autoFillTitle = false, +}: OwnProps) { + const { data } = useGetActivityQuery({ + variables: { + activityId: activityId ?? '', + }, + skip: !activityId, + }); + const activity = data?.findManyActivities[0]; + const [hasUserManuallySetTitle, setHasUserManuallySetTitle] = + useState(false); + + const [title, setTitle] = useState(null); + + useEffect(() => { + if (!hasUserManuallySetTitle) { + setTitle(activity?.title ?? ''); + } + }, [setTitle, activity?.title, hasUserManuallySetTitle]); + + const [updateActivityMutation] = useUpdateActivityMutation(); + + const debounceUpdateTitle = useMemo(() => { + function updateTitle(title: string) { + if (activity) { + updateActivityMutation({ + variables: { + id: activityId, + title: title ?? '', + }, + refetchQueries: [getOperationName(GET_ACTIVITY) ?? ''], + optimisticResponse: { + __typename: 'Mutation', + updateOneActivity: { + __typename: 'Activity', + id: activityId, + title: title, + type: activity.type, + }, + }, + }); + } + } + return debounce(updateTitle, 200); + }, [activityId, updateActivityMutation, activity]); + + function updateTitleFromBody(body: string) { + const parsedTitle = JSON.parse(body)[0]?.content[0]?.text; + if (!hasUserManuallySetTitle && autoFillTitle) { + setTitle(parsedTitle); + debounceUpdateTitle(parsedTitle); + } + } + + if (!activity) { + return <>; + } + + return ( + + + + + + + + { + setHasUserManuallySetTitle(true); + setTitle(event.target.value); + debounceUpdateTitle(event.target.value); + }} + value={title ?? ''} + /> + + } + value={ + + } + label="Relations" + /> + + + + + {showComment && ( + + )} + + ); +} diff --git a/front/src/modules/activities/right-drawer/components/CommentThreadActionBar.tsx b/front/src/modules/activities/right-drawer/components/ActivityActionBar.tsx similarity index 70% rename from front/src/modules/activities/right-drawer/components/CommentThreadActionBar.tsx rename to front/src/modules/activities/right-drawer/components/ActivityActionBar.tsx index b0ec700c4..877140358 100644 --- a/front/src/modules/activities/right-drawer/components/CommentThreadActionBar.tsx +++ b/front/src/modules/activities/right-drawer/components/ActivityActionBar.tsx @@ -3,13 +3,13 @@ import { useTheme } from '@emotion/react'; import styled from '@emotion/styled'; import { useRecoilState } from 'recoil'; -import { GET_COMMENT_THREADS_BY_TARGETS } from '@/activities/queries'; +import { GET_ACTIVITIES_BY_TARGETS } from '@/activities/queries'; import { GET_COMPANIES } from '@/companies/queries'; import { GET_PEOPLE } from '@/people/queries'; import { Button, ButtonVariant } from '@/ui/button/components/Button'; import { IconTrash } from '@/ui/icon'; import { isRightDrawerOpenState } from '@/ui/right-drawer/states/isRightDrawerOpenState'; -import { useDeleteCommentThreadMutation } from '~/generated/graphql'; +import { useDeleteActivityMutation } from '~/generated/graphql'; const StyledContainer = styled.div` color: ${({ theme }) => theme.font.color.tertiary}; @@ -17,21 +17,21 @@ const StyledContainer = styled.div` `; type OwnProps = { - commentThreadId: string; + activityId: string; }; -export function CommentThreadActionBar({ commentThreadId }: OwnProps) { +export function ActivityActionBar({ activityId }: OwnProps) { const theme = useTheme(); - const [createCommentMutation] = useDeleteCommentThreadMutation(); + const [createCommentMutation] = useDeleteActivityMutation(); const [, setIsRightDrawerOpen] = useRecoilState(isRightDrawerOpenState); - function deleteCommentThread() { + function deleteActivity() { createCommentMutation({ - variables: { commentThreadId }, + variables: { activityId }, refetchQueries: [ getOperationName(GET_COMPANIES) ?? '', getOperationName(GET_PEOPLE) ?? '', - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', + getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? '', ], }); setIsRightDrawerOpen(false); @@ -43,7 +43,7 @@ export function CommentThreadActionBar({ commentThreadId }: OwnProps) { icon={ } - onClick={deleteCommentThread} + onClick={deleteActivity} variant={ButtonVariant.Tertiary} /> diff --git a/front/src/modules/activities/right-drawer/components/CommentThread.tsx b/front/src/modules/activities/right-drawer/components/CommentThread.tsx deleted file mode 100644 index 1a8c4e6d0..000000000 --- a/front/src/modules/activities/right-drawer/components/CommentThread.tsx +++ /dev/null @@ -1,34 +0,0 @@ -import { CommentThreadEditor } from '@/activities/components/CommentThreadEditor'; -import { useGetCommentThreadQuery } from '~/generated/graphql'; - -import '@blocknote/core/style.css'; - -type OwnProps = { - commentThreadId: string; - showComment?: boolean; - autoFillTitle?: boolean; -}; - -export function CommentThread({ - commentThreadId, - showComment = true, - autoFillTitle = false, -}: OwnProps) { - const { data } = useGetCommentThreadQuery({ - variables: { - commentThreadId: commentThreadId ?? '', - }, - skip: !commentThreadId, - }); - const commentThread = data?.findManyCommentThreads[0]; - - return commentThread ? ( - - ) : ( - <> - ); -} diff --git a/front/src/modules/activities/right-drawer/components/create/RightDrawerCreateCommentThread.tsx b/front/src/modules/activities/right-drawer/components/create/RightDrawerCreateActivity.tsx similarity index 58% rename from front/src/modules/activities/right-drawer/components/create/RightDrawerCreateCommentThread.tsx rename to front/src/modules/activities/right-drawer/components/create/RightDrawerCreateActivity.tsx index 1e92d71d7..86f4aafc3 100644 --- a/front/src/modules/activities/right-drawer/components/create/RightDrawerCreateCommentThread.tsx +++ b/front/src/modules/activities/right-drawer/components/create/RightDrawerCreateActivity.tsx @@ -1,22 +1,22 @@ import { useRecoilValue } from 'recoil'; -import { viewableCommentThreadIdState } from '@/activities/states/viewableCommentThreadIdState'; +import { viewableActivityIdState } from '@/activities/states/viewableActivityIdState'; import { RightDrawerBody } from '@/ui/right-drawer/components/RightDrawerBody'; import { RightDrawerPage } from '@/ui/right-drawer/components/RightDrawerPage'; import { RightDrawerTopBar } from '@/ui/right-drawer/components/RightDrawerTopBar'; -import { CommentThread } from '../CommentThread'; +import { Activity } from '../Activity'; -export function RightDrawerCreateCommentThread() { - const commentThreadId = useRecoilValue(viewableCommentThreadIdState); +export function RightDrawerCreateActivity() { + const activityId = useRecoilValue(viewableActivityIdState); return ( - {commentThreadId && ( - diff --git a/front/src/modules/activities/right-drawer/components/edit/RightDrawerEditCommentThread.tsx b/front/src/modules/activities/right-drawer/components/edit/RightDrawerEditActivity.tsx similarity index 55% rename from front/src/modules/activities/right-drawer/components/edit/RightDrawerEditCommentThread.tsx rename to front/src/modules/activities/right-drawer/components/edit/RightDrawerEditActivity.tsx index eaf5d7928..9d104339c 100644 --- a/front/src/modules/activities/right-drawer/components/edit/RightDrawerEditCommentThread.tsx +++ b/front/src/modules/activities/right-drawer/components/edit/RightDrawerEditActivity.tsx @@ -1,20 +1,20 @@ import { useRecoilValue } from 'recoil'; -import { viewableCommentThreadIdState } from '@/activities/states/viewableCommentThreadIdState'; +import { viewableActivityIdState } from '@/activities/states/viewableActivityIdState'; import { RightDrawerBody } from '@/ui/right-drawer/components/RightDrawerBody'; import { RightDrawerPage } from '@/ui/right-drawer/components/RightDrawerPage'; import { RightDrawerTopBar } from '@/ui/right-drawer/components/RightDrawerTopBar'; -import { CommentThread } from '../CommentThread'; +import { Activity } from '../Activity'; -export function RightDrawerEditCommentThread() { - const commentThreadId = useRecoilValue(viewableCommentThreadIdState); +export function RightDrawerEditActivity() { + const activityId = useRecoilValue(viewableActivityIdState); return ( - {commentThreadId && } + {activityId && } ); diff --git a/front/src/modules/activities/states/commentableEntityArrayState.ts b/front/src/modules/activities/states/commentableEntityArrayState.ts index 1a82760e7..987bb9a3d 100644 --- a/front/src/modules/activities/states/commentableEntityArrayState.ts +++ b/front/src/modules/activities/states/commentableEntityArrayState.ts @@ -3,6 +3,6 @@ import { atom } from 'recoil'; import { CommentableEntity } from '../types/CommentableEntity'; export const commentableEntityArrayState = atom({ - key: 'comments/commentable-entity-array', + key: 'activities/commentable-entity-array', default: [], }); diff --git a/front/src/modules/activities/states/viewableActivityIdState.ts b/front/src/modules/activities/states/viewableActivityIdState.ts new file mode 100644 index 000000000..95cfc1712 --- /dev/null +++ b/front/src/modules/activities/states/viewableActivityIdState.ts @@ -0,0 +1,6 @@ +import { atom } from 'recoil'; + +export const viewableActivityIdState = atom({ + key: 'activities/viewable-activity-id', + default: null, +}); diff --git a/front/src/modules/activities/states/viewableCommentThreadIdState.ts b/front/src/modules/activities/states/viewableCommentThreadIdState.ts deleted file mode 100644 index 0caff9973..000000000 --- a/front/src/modules/activities/states/viewableCommentThreadIdState.ts +++ /dev/null @@ -1,6 +0,0 @@ -import { atom } from 'recoil'; - -export const viewableCommentThreadIdState = atom({ - key: 'comments/viewable-comment-thread-id', - default: null, -}); diff --git a/front/src/modules/activities/timeline/components/Timeline.tsx b/front/src/modules/activities/timeline/components/Timeline.tsx index 36ab0f61c..b9307bb3e 100644 --- a/front/src/modules/activities/timeline/components/Timeline.tsx +++ b/front/src/modules/activities/timeline/components/Timeline.tsx @@ -2,16 +2,16 @@ import React from 'react'; import { useTheme } from '@emotion/react'; import styled from '@emotion/styled'; -import { CommentThreadCreateButton } from '@/activities/components/CommentThreadCreateButton'; -import { useOpenCreateCommentThreadDrawer } from '@/activities/hooks/useOpenCreateCommentThreadDrawer'; +import { ActivityCreateButton } from '@/activities/components/ActivityCreateButton'; +import { useOpenCreateActivityDrawer } from '@/activities/hooks/useOpenCreateActivityDrawer'; +import { ActivityForDrawer } from '@/activities/types/ActivityForDrawer'; import { CommentableEntity } from '@/activities/types/CommentableEntity'; -import { CommentThreadForDrawer } from '@/activities/types/CommentThreadForDrawer'; import { useIsMobile } from '@/ui/hooks/useIsMobile'; import { IconCircleDot } from '@/ui/icon'; import { ActivityType, SortOrder, - useGetCommentThreadsByTargetsQuery, + useGetActivitiesByTargetsQuery, } from '~/generated/graphql'; import { TimelineActivity } from './TimelineActivity'; @@ -96,9 +96,9 @@ const StyledStartIcon = styled.div` export function Timeline({ entity }: { entity: CommentableEntity }) { const theme = useTheme(); - const { data: queryResult, loading } = useGetCommentThreadsByTargetsQuery({ + const { data: queryResult, loading } = useGetActivitiesByTargetsQuery({ variables: { - commentThreadTargetIds: [entity.id], + activityTargetIds: [entity.id], orderBy: [ { createdAt: SortOrder.Desc, @@ -107,21 +107,20 @@ export function Timeline({ entity }: { entity: CommentableEntity }) { }, }); - const openCreateCommandThread = useOpenCreateCommentThreadDrawer(); + const openCreateCommandThread = useOpenCreateActivityDrawer(); - const commentThreads: CommentThreadForDrawer[] = - queryResult?.findManyCommentThreads ?? []; + const activities: ActivityForDrawer[] = queryResult?.findManyActivities ?? []; if (loading) { return <>; } - if (!commentThreads.length) { + if (!activities.length) { return ( No activity yet Create one: - openCreateCommandThread(entity, ActivityType.Note)} onTaskClick={() => openCreateCommandThread(entity, ActivityType.Task)} /> @@ -132,17 +131,14 @@ export function Timeline({ entity }: { entity: CommentableEntity }) { return ( - openCreateCommandThread(entity, ActivityType.Note)} onTaskClick={() => openCreateCommandThread(entity, ActivityType.Task)} /> - {commentThreads.map((commentThread) => ( - + {activities.map((activity) => ( + ))} diff --git a/front/src/modules/activities/timeline/components/TimelineActivity.tsx b/front/src/modules/activities/timeline/components/TimelineActivity.tsx index 1f7a738c7..d1d6829cf 100644 --- a/front/src/modules/activities/timeline/components/TimelineActivity.tsx +++ b/front/src/modules/activities/timeline/components/TimelineActivity.tsx @@ -3,14 +3,11 @@ import { Tooltip } from 'react-tooltip'; import { getOperationName } from '@apollo/client/utilities'; import styled from '@emotion/styled'; -import { useOpenCommentThreadRightDrawer } from '@/activities/hooks/useOpenCommentThreadRightDrawer'; -import { GET_COMMENT_THREADS_BY_TARGETS } from '@/activities/queries'; +import { useOpenActivityRightDrawer } from '@/activities/hooks/useOpenActivityRightDrawer'; +import { GET_ACTIVITIES_BY_TARGETS } from '@/activities/queries'; import { IconNotes } from '@/ui/icon'; import { OverflowingTextWithTooltip } from '@/ui/tooltip/OverflowingTextWithTooltip'; -import { - CommentThread, - useUpdateCommentThreadMutation, -} from '~/generated/graphql'; +import { Activity, useUpdateActivityMutation } from '~/generated/graphql'; import { beautifyExactDate, beautifyPastDateRelativeToNow, @@ -115,35 +112,31 @@ const StyledTimelineItemContainer = styled.div` `; type OwnProps = { - commentThread: Pick< - CommentThread, + activity: Pick< + Activity, 'id' | 'title' | 'body' | 'createdAt' | 'completedAt' | 'type' - > & { author: Pick }; + > & { author: Pick }; }; -export function TimelineActivity({ commentThread }: OwnProps) { - const beautifiedCreatedAt = beautifyPastDateRelativeToNow( - commentThread.createdAt, - ); - const exactCreatedAt = beautifyExactDate(commentThread.createdAt); - const body = JSON.parse(commentThread.body ?? '{}')[0]?.content[0]?.text; +export function TimelineActivity({ activity }: OwnProps) { + const beautifiedCreatedAt = beautifyPastDateRelativeToNow(activity.createdAt); + const exactCreatedAt = beautifyExactDate(activity.createdAt); + const body = JSON.parse(activity.body ?? '{}')[0]?.content[0]?.text; - const openCommentThreadRightDrawer = useOpenCommentThreadRightDrawer(); - const [updateCommentThreadMutation] = useUpdateCommentThreadMutation(); + const openActivityRightDrawer = useOpenActivityRightDrawer(); + const [updateActivityMutation] = useUpdateActivityMutation(); const handleActivityCompletionChange = useCallback( (value: boolean) => { - updateCommentThreadMutation({ + updateActivityMutation({ variables: { - id: commentThread.id, + id: activity.id, completedAt: value ? new Date().toISOString() : null, }, - refetchQueries: [ - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', - ], + refetchQueries: [getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? ''], }); }, - [commentThread, updateCommentThreadMutation], + [activity, updateActivityMutation], ); return ( @@ -153,14 +146,14 @@ export function TimelineActivity({ commentThread }: OwnProps) { - {commentThread.author.displayName} - created a {commentThread.type.toLowerCase()} + {activity.author.displayName} + created a note created a {activity.type.toLowerCase()} - + {beautifiedCreatedAt} ago - openCommentThreadRightDrawer(commentThread.id)} - > + openActivityRightDrawer(activity.id)}> diff --git a/front/src/modules/activities/types/ActivityForDrawer.ts b/front/src/modules/activities/types/ActivityForDrawer.ts new file mode 100644 index 000000000..1acda21af --- /dev/null +++ b/front/src/modules/activities/types/ActivityForDrawer.ts @@ -0,0 +1,4 @@ +import { GetActivitiesByTargetsQuery } from '~/generated/graphql'; + +export type ActivityForDrawer = + GetActivitiesByTargetsQuery['findManyActivities'][0]; diff --git a/front/src/modules/activities/types/CommentForDrawer.ts b/front/src/modules/activities/types/CommentForDrawer.ts index 95ff1f1d7..4ee240d72 100644 --- a/front/src/modules/activities/types/CommentForDrawer.ts +++ b/front/src/modules/activities/types/CommentForDrawer.ts @@ -1,5 +1,3 @@ -import { CommentThreadForDrawer } from './CommentThreadForDrawer'; +import { ActivityForDrawer } from './ActivityForDrawer'; -export type CommentForDrawer = NonNullable< - CommentThreadForDrawer['comments'] ->[0]; +export type CommentForDrawer = NonNullable[0]; diff --git a/front/src/modules/activities/types/CommentThreadForDrawer.ts b/front/src/modules/activities/types/CommentThreadForDrawer.ts deleted file mode 100644 index 79f969300..000000000 --- a/front/src/modules/activities/types/CommentThreadForDrawer.ts +++ /dev/null @@ -1,4 +0,0 @@ -import { GetCommentThreadsByTargetsQuery } from '~/generated/graphql'; - -export type CommentThreadForDrawer = - GetCommentThreadsByTargetsQuery['findManyCommentThreads'][0]; diff --git a/front/src/modules/apollo/hooks/useApolloFactory.ts b/front/src/modules/apollo/hooks/useApolloFactory.ts index 4eb0d6b9d..a4c7e6aa0 100644 --- a/front/src/modules/apollo/hooks/useApolloFactory.ts +++ b/front/src/modules/apollo/hooks/useApolloFactory.ts @@ -6,7 +6,7 @@ import { useRecoilState } from 'recoil'; import { tokenPairState } from '@/auth/states/tokenPairState'; import { isDebugModeState } from '@/client-config/states/isDebugModeState'; import { AppPath } from '@/types/AppPath'; -import { CommentThreadTarget } from '~/generated/graphql'; +import { ActivityTarget } from '~/generated/graphql'; import { useIsMatchingLocation } from '~/hooks/useIsMatchingLocation'; import { useUpdateEffect } from '~/hooks/useUpdateEffect'; @@ -25,12 +25,12 @@ export function useApolloFactory() { uri: `${process.env.REACT_APP_API_URL}`, cache: new InMemoryCache({ typePolicies: { - CommentThread: { + Activity: { fields: { - commentThreadTargets: { + activityTargets: { merge( - _existing: CommentThreadTarget[] = [], - incoming: CommentThreadTarget[], + _existing: ActivityTarget[] = [], + incoming: ActivityTarget[], ) { return [...incoming]; }, diff --git a/front/src/modules/companies/components/CompanyEditableNameCell.tsx b/front/src/modules/companies/components/CompanyEditableNameCell.tsx index fbea17c39..e7956bbf8 100644 --- a/front/src/modules/companies/components/CompanyEditableNameCell.tsx +++ b/front/src/modules/companies/components/CompanyEditableNameCell.tsx @@ -14,7 +14,7 @@ import { CompanyChip } from './CompanyChip'; type OwnProps = { company: Pick< GetCompaniesQuery['companies'][0], - 'id' | 'name' | 'domainName' | '_commentThreadCount' + 'id' | 'name' | 'domainName' | '_activityCount' >; }; diff --git a/front/src/modules/companies/queries/select.ts b/front/src/modules/companies/queries/select.ts index 163f59116..fdecd5e07 100644 --- a/front/src/modules/companies/queries/select.ts +++ b/front/src/modules/companies/queries/select.ts @@ -28,7 +28,7 @@ export const GET_COMPANIES = gql` address linkedinUrl employees - _commentThreadCount + _activityCount accountOwner { id email diff --git a/front/src/modules/companies/queries/show.ts b/front/src/modules/companies/queries/show.ts index 4344b5b2a..73fc25a12 100644 --- a/front/src/modules/companies/queries/show.ts +++ b/front/src/modules/companies/queries/show.ts @@ -12,7 +12,7 @@ export const GET_COMPANY = gql` address linkedinUrl employees - _commentThreadCount + _activityCount accountOwner { id email diff --git a/front/src/modules/companies/table/components/EditableCompanyNameCell.tsx b/front/src/modules/companies/table/components/EditableCompanyNameCell.tsx index d2c2dcca0..df25d15f0 100644 --- a/front/src/modules/companies/table/components/EditableCompanyNameCell.tsx +++ b/front/src/modules/companies/table/components/EditableCompanyNameCell.tsx @@ -25,7 +25,7 @@ export function EditableCompanyNameCell() { id: currentRowEntityId ?? '', name: name ?? '', domainName: domainName ?? '', - _commentThreadCount: commentCount ?? 0, + _activityCount: commentCount ?? 0, }} /> ); diff --git a/front/src/modules/companies/table/components/TableActionBarButtonCreateActivityCompany.tsx b/front/src/modules/companies/table/components/TableActionBarButtonCreateActivityCompany.tsx new file mode 100644 index 000000000..b06dafaef --- /dev/null +++ b/front/src/modules/companies/table/components/TableActionBarButtonCreateActivityCompany.tsx @@ -0,0 +1,14 @@ +import { useOpenCreateActivityDrawerForSelectedRowIds } from '@/activities/hooks/useOpenCreateActivityDrawerForSelectedRowIds'; +import { TableActionBarButtonToggleComments } from '@/ui/table/action-bar/components/TableActionBarButtonOpenComments'; +import { CommentableType } from '~/generated/graphql'; + +export function TableActionBarButtonCreateActivityCompany() { + const openCreateActivityRightDrawer = + useOpenCreateActivityDrawerForSelectedRowIds(); + + async function handleButtonClick() { + openCreateActivityRightDrawer(CommentableType.Company); + } + + return ; +} diff --git a/front/src/modules/companies/table/components/TableActionBarButtonCreateCommentThreadCompany.tsx b/front/src/modules/companies/table/components/TableActionBarButtonCreateCommentThreadCompany.tsx deleted file mode 100644 index 06ba20b64..000000000 --- a/front/src/modules/companies/table/components/TableActionBarButtonCreateCommentThreadCompany.tsx +++ /dev/null @@ -1,14 +0,0 @@ -import { useOpenCreateCommentThreadDrawerForSelectedRowIds } from '@/activities/hooks/useOpenCreateCommentDrawerForSelectedRowIds'; -import { TableActionBarButtonToggleComments } from '@/ui/table/action-bar/components/TableActionBarButtonOpenComments'; -import { CommentableType } from '~/generated/graphql'; - -export function TableActionBarButtonCreateCommentThreadCompany() { - const openCreateCommentThreadRightDrawer = - useOpenCreateCommentThreadDrawerForSelectedRowIds(); - - async function handleButtonClick() { - openCreateCommentThreadRightDrawer(CommentableType.Company); - } - - return ; -} diff --git a/front/src/modules/companies/table/components/companies-mock-data.ts b/front/src/modules/companies/table/components/companies-mock-data.ts index e69bbcb03..9455a3920 100644 --- a/front/src/modules/companies/table/components/companies-mock-data.ts +++ b/front/src/modules/companies/table/components/companies-mock-data.ts @@ -10,7 +10,7 @@ type MockedCompany = Pick< | 'address' | 'employees' | 'linkedinUrl' - | '_commentThreadCount' + | '_activityCount' > & { accountOwner: Pick< User, @@ -33,7 +33,7 @@ export const mockedCompaniesData: Array = [ createdAt: '2023-04-26T10:08:54.724515+00:00', address: 'San Francisco, CA', employees: 5000, - _commentThreadCount: 0, + _activityCount: 0, accountOwner: { email: 'charles@test.com', displayName: 'Charles Test', @@ -53,7 +53,7 @@ export const mockedCompaniesData: Array = [ createdAt: '2023-04-26T10:12:42.33625+00:00', address: 'Paris, France', employees: 800, - _commentThreadCount: 0, + _activityCount: 0, accountOwner: null, __typename: 'Company', }, @@ -65,7 +65,7 @@ export const mockedCompaniesData: Array = [ createdAt: '2023-04-26T10:10:32.530184+00:00', address: 'San Francisco, CA', employees: 8000, - _commentThreadCount: 0, + _activityCount: 0, accountOwner: null, __typename: 'Company', }, @@ -77,7 +77,7 @@ export const mockedCompaniesData: Array = [ createdAt: '2023-03-21T06:30:25.39474+00:00', address: 'San Francisco, CA', employees: 800, - _commentThreadCount: 0, + _activityCount: 0, accountOwner: null, __typename: 'Company', }, @@ -89,7 +89,7 @@ export const mockedCompaniesData: Array = [ createdAt: '2023-04-26T10:13:29.712485+00:00', address: 'San Francisco, CA', employees: 400, - _commentThreadCount: 0, + _activityCount: 0, accountOwner: null, __typename: 'Company', }, diff --git a/front/src/modules/companies/table/hooks/useSetCompanyEntityTable.ts b/front/src/modules/companies/table/hooks/useSetCompanyEntityTable.ts index 8c04826cc..21a66b2bb 100644 --- a/front/src/modules/companies/table/hooks/useSetCompanyEntityTable.ts +++ b/front/src/modules/companies/table/hooks/useSetCompanyEntityTable.ts @@ -83,10 +83,10 @@ export function useSetCompanyEntityTable() { .getLoadable(companyCommentCountFamilyState(company.id)) .valueOrThrow(); - if (currentCommentCount !== company._commentThreadCount) { + if (currentCommentCount !== company._activityCount) { set( companyCommentCountFamilyState(company.id), - company._commentThreadCount, + company._activityCount, ); } diff --git a/front/src/modules/people/components/EditablePeopleFullName.tsx b/front/src/modules/people/components/EditablePeopleFullName.tsx index 7d8c0891a..a8ae1b678 100644 --- a/front/src/modules/people/components/EditablePeopleFullName.tsx +++ b/front/src/modules/people/components/EditablePeopleFullName.tsx @@ -10,11 +10,7 @@ type OwnProps = { | Partial< Pick< Person, - | 'id' - | 'firstName' - | 'lastName' - | 'displayName' - | '_commentThreadCount' + 'id' | 'firstName' | 'lastName' | 'displayName' | '_activityCount' > > | null diff --git a/front/src/modules/people/hooks/useSetPeopleEntityTable.ts b/front/src/modules/people/hooks/useSetPeopleEntityTable.ts index c6f215983..1c013fbe6 100644 --- a/front/src/modules/people/hooks/useSetPeopleEntityTable.ts +++ b/front/src/modules/people/hooks/useSetPeopleEntityTable.ts @@ -101,12 +101,12 @@ export function useSetPeopleEntityTable() { if ( currentNameCell.firstName !== person.firstName || currentNameCell.lastName !== person.lastName || - currentNameCell.commentCount !== person._commentThreadCount + currentNameCell.commentCount !== person._activityCount ) { set(peopleNameCellFamilyState(person.id), { firstName: person.firstName ?? null, lastName: person.lastName ?? null, - commentCount: person._commentThreadCount, + commentCount: person._activityCount, displayName: person.displayName ?? null, }); } diff --git a/front/src/modules/people/queries/select.ts b/front/src/modules/people/queries/select.ts index c4aa5e4c9..eb4169072 100644 --- a/front/src/modules/people/queries/select.ts +++ b/front/src/modules/people/queries/select.ts @@ -31,7 +31,7 @@ export const GET_PEOPLE = gql` jobTitle linkedinUrl createdAt - _commentThreadCount + _activityCount company { id name @@ -107,7 +107,7 @@ export const GET_PERSON_NAMES_AND_COMMENT_COUNT = gql` firstName lastName displayName - _commentThreadCount + _activityCount } } `; @@ -129,7 +129,7 @@ export const GET_PERSON_COMMENT_COUNT = gql` query GetPersonCommentCountById($id: String!) { person: findUniquePerson(id: $id) { id - _commentThreadCount + _activityCount } } `; diff --git a/front/src/modules/people/queries/show.ts b/front/src/modules/people/queries/show.ts index 271d4a43b..03b94bf60 100644 --- a/front/src/modules/people/queries/show.ts +++ b/front/src/modules/people/queries/show.ts @@ -15,7 +15,7 @@ export const GET_PERSON = gql` jobTitle linkedinUrl phone - _commentThreadCount + _activityCount company { id name diff --git a/front/src/modules/people/table/components/EditablePeopleFullNameCell.tsx b/front/src/modules/people/table/components/EditablePeopleFullNameCell.tsx index 5730bc9f1..a1ee9a097 100644 --- a/front/src/modules/people/table/components/EditablePeopleFullNameCell.tsx +++ b/front/src/modules/people/table/components/EditablePeopleFullNameCell.tsx @@ -21,7 +21,7 @@ export function EditablePeopleFullNameCell() { ; +} diff --git a/front/src/modules/people/table/components/TableActionBarButtonCreateCommentThreadPeople.tsx b/front/src/modules/people/table/components/TableActionBarButtonCreateCommentThreadPeople.tsx deleted file mode 100644 index 178ac7ece..000000000 --- a/front/src/modules/people/table/components/TableActionBarButtonCreateCommentThreadPeople.tsx +++ /dev/null @@ -1,14 +0,0 @@ -import { useOpenCreateCommentThreadDrawerForSelectedRowIds } from '@/activities/hooks/useOpenCreateCommentDrawerForSelectedRowIds'; -import { TableActionBarButtonToggleComments } from '@/ui/table/action-bar/components/TableActionBarButtonOpenComments'; -import { CommentableType } from '~/generated/graphql'; - -export function TableActionBarButtonCreateCommentThreadPeople() { - const openCreateCommentThreadRightDrawer = - useOpenCreateCommentThreadDrawerForSelectedRowIds(); - - async function handleButtonClick() { - openCreateCommentThreadRightDrawer(CommentableType.Person); - } - - return ; -} diff --git a/front/src/modules/ui/button/components/DropdownButton.tsx b/front/src/modules/ui/button/components/DropdownButton.tsx new file mode 100644 index 000000000..232ff6d82 --- /dev/null +++ b/front/src/modules/ui/button/components/DropdownButton.tsx @@ -0,0 +1,144 @@ +import React, { useEffect, useState } from 'react'; +import styled from '@emotion/styled'; + +import { IconChevronDown } from '@/ui/icon/index'; + +type ButtonProps = React.ComponentProps<'button'>; + +export type DropdownOptionType = { + key: string; + label: string; + icon: React.ReactNode; +}; + +type OwnProps = { + options: DropdownOptionType[]; + selectedOptionKey?: string; + onSelection: (value: DropdownOptionType) => void; +} & ButtonProps; + +const StyledButton = styled.button` + align-items: center; + background: ${({ theme }) => theme.background.tertiary}; + border: 1px solid ${({ theme }) => theme.border.color.medium}; + border-bottom-left-radius: ${({ isOpen, theme }) => + isOpen ? 0 : theme.border.radius.sm}; + border-bottom-right-radius: ${({ isOpen, theme }) => + isOpen ? 0 : theme.border.radius.sm}; + border-top-left-radius: ${({ theme }) => theme.border.radius.sm}; + border-top-right-radius: ${({ theme }) => theme.border.radius.sm}; + color: ${({ theme }) => theme.font.color.secondary}; + cursor: pointer; + display: flex; + gap: ${({ theme }) => theme.spacing(2)}; + padding: ${({ theme }) => theme.spacing(1)} ${({ theme }) => theme.spacing(2)}; + + svg { + align-items: center; + display: flex; + height: 14px; + justify-content: center; + width: 14px; + } +`; + +const StyledDropdownItem = styled.button` + align-items: center; + background: ${({ theme }) => theme.background.tertiary}; + border: 1px solid ${({ theme }) => theme.border.color.medium}; + border-radius: ${({ theme }) => theme.border.radius.sm}; + border-top: none; + border-top-left-radius: 0; + border-top-right-radius: 0; + color: ${({ theme }) => theme.font.color.secondary}; + cursor: pointer; + display: flex; + gap: ${({ theme }) => theme.spacing(2)}; + padding: ${({ theme }) => theme.spacing(1)} ${({ theme }) => theme.spacing(2)}; + + svg { + align-items: center; + display: flex; + height: 14px; + justify-content: center; + width: 14px; + } +`; + +const DropdownContainer = styled.div` + position: relative; +`; + +const DropdownMenu = styled.div` + display: flex; + flex-direction: column; + position: absolute; + width: 100%; +`; + +export function DropdownButton({ + options, + selectedOptionKey, + onSelection, + ...buttonProps +}: OwnProps) { + const [isOpen, setIsOpen] = useState(false); + const [selectedOption, setSelectedOption] = useState< + DropdownOptionType | undefined + >(undefined); + + useEffect(() => { + if (selectedOptionKey) { + const option = options.find((option) => option.key === selectedOptionKey); + setSelectedOption(option); + } else { + setSelectedOption(options[0]); + } + }, [selectedOptionKey, options]); + + if (!options.length) { + throw new Error('You must provide at least one option.'); + } + + const handleSelect = + (option: DropdownOptionType) => + (event: React.MouseEvent) => { + event.preventDefault(); + onSelection(option); + setSelectedOption(option); + setIsOpen(false); + }; + + return ( + <> + {selectedOption && ( + + setIsOpen(!isOpen)} + {...buttonProps} + isOpen={isOpen} + > + {selectedOption.icon} + {selectedOption.label} + {options.length > 1 && } + + {isOpen && ( + + {options + .filter((option) => option.label !== selectedOption.label) + .map((option, index) => ( + + {option.icon} + {option.label} + + ))} + + )} + + )} + + ); +} diff --git a/front/src/modules/ui/right-drawer/components/RightDrawerRouter.tsx b/front/src/modules/ui/right-drawer/components/RightDrawerRouter.tsx index 20a9b07a5..a47bcada0 100644 --- a/front/src/modules/ui/right-drawer/components/RightDrawerRouter.tsx +++ b/front/src/modules/ui/right-drawer/components/RightDrawerRouter.tsx @@ -1,7 +1,7 @@ import { useRecoilState } from 'recoil'; -import { RightDrawerCreateCommentThread } from '@/activities/right-drawer/components/create/RightDrawerCreateCommentThread'; -import { RightDrawerEditCommentThread } from '@/activities/right-drawer/components/edit/RightDrawerEditCommentThread'; +import { RightDrawerCreateActivity } from '@/activities/right-drawer/components/create/RightDrawerCreateActivity'; +import { RightDrawerEditActivity } from '@/activities/right-drawer/components/edit/RightDrawerEditActivity'; import { RightDrawerTimeline } from '@/activities/right-drawer/components/RightDrawerTimeline'; import { isDefined } from '~/utils/isDefined'; @@ -18,10 +18,10 @@ export function RightDrawerRouter() { switch (rightDrawerPage) { case RightDrawerPages.Timeline: return ; - case RightDrawerPages.CreateCommentThread: - return ; - case RightDrawerPages.EditCommentThread: - return ; + case RightDrawerPages.CreateActivity: + return ; + case RightDrawerPages.EditActivity: + return ; default: return <>; } diff --git a/front/src/modules/ui/right-drawer/types/RightDrawerPages.ts b/front/src/modules/ui/right-drawer/types/RightDrawerPages.ts index a260334e9..d793aa7fb 100644 --- a/front/src/modules/ui/right-drawer/types/RightDrawerPages.ts +++ b/front/src/modules/ui/right-drawer/types/RightDrawerPages.ts @@ -1,5 +1,5 @@ export enum RightDrawerPages { Timeline = 'timeline', - CreateCommentThread = 'create-comment-thread', - EditCommentThread = 'edit-comment-thread', + CreateActivity = 'create-activity', + EditActivity = 'edit-activity', } diff --git a/front/src/modules/ui/table/editable-cell/types/EditableChip.tsx b/front/src/modules/ui/table/editable-cell/types/EditableChip.tsx index 62e4816c8..1173c2caa 100644 --- a/front/src/modules/ui/table/editable-cell/types/EditableChip.tsx +++ b/front/src/modules/ui/table/editable-cell/types/EditableChip.tsx @@ -9,7 +9,7 @@ export type EditableChipProps = { value: string; editModeHorizontalAlign?: 'left' | 'right'; ChipComponent: React.ReactNode; - commentThreadCount?: number; + activityCount?: number; onCommentClick?: (event: React.MouseEvent) => void; rightEndContents?: ReactNode[]; onSubmit?: (newValue: string) => void; diff --git a/front/src/pages/companies/Companies.tsx b/front/src/pages/companies/Companies.tsx index cde2c8541..ec0cd3624 100644 --- a/front/src/pages/companies/Companies.tsx +++ b/front/src/pages/companies/Companies.tsx @@ -4,7 +4,7 @@ import styled from '@emotion/styled'; import { GET_COMPANIES } from '@/companies/queries'; import { CompanyTable } from '@/companies/table/components/CompanyTable'; -import { TableActionBarButtonCreateCommentThreadCompany } from '@/companies/table/components/TableActionBarButtonCreateCommentThreadCompany'; +import { TableActionBarButtonCreateActivityCompany } from '@/companies/table/components/TableActionBarButtonCreateActivityCompany'; import { TableActionBarButtonDeleteCompanies } from '@/companies/table/components/TableActionBarButtonDeleteCompanies'; import { IconBuildingSkyscraper } from '@/ui/icon'; import { WithTopBarContainer } from '@/ui/layout/components/WithTopBarContainer'; @@ -53,7 +53,7 @@ export function Companies() { - + diff --git a/front/src/pages/companies/CompaniesMockMode.tsx b/front/src/pages/companies/CompaniesMockMode.tsx index d64cd9104..1682eb3a4 100644 --- a/front/src/pages/companies/CompaniesMockMode.tsx +++ b/front/src/pages/companies/CompaniesMockMode.tsx @@ -2,7 +2,7 @@ import { useTheme } from '@emotion/react'; import styled from '@emotion/styled'; import { CompanyTableMockMode } from '@/companies/table/components/CompanyTableMockMode'; -import { TableActionBarButtonCreateCommentThreadCompany } from '@/companies/table/components/TableActionBarButtonCreateCommentThreadCompany'; +import { TableActionBarButtonCreateActivityCompany } from '@/companies/table/components/TableActionBarButtonCreateActivityCompany'; import { TableActionBarButtonDeleteCompanies } from '@/companies/table/components/TableActionBarButtonDeleteCompanies'; import { IconBuildingSkyscraper } from '@/ui/icon'; import { WithTopBarContainer } from '@/ui/layout/components/WithTopBarContainer'; @@ -29,7 +29,7 @@ export function CompaniesMockMode() { - + diff --git a/front/src/pages/companies/__stories__/Company.stories.tsx b/front/src/pages/companies/__stories__/Company.stories.tsx index 4adc139c3..6efd7faff 100644 --- a/front/src/pages/companies/__stories__/Company.stories.tsx +++ b/front/src/pages/companies/__stories__/Company.stories.tsx @@ -4,18 +4,15 @@ import type { Meta, StoryObj } from '@storybook/react'; import { fireEvent, within } from '@storybook/testing-library'; import { graphql } from 'msw'; -import { - GET_COMMENT_THREAD, - GET_COMMENT_THREADS_BY_TARGETS, -} from '@/activities/queries'; -import { CREATE_COMMENT_THREAD_WITH_COMMENT } from '@/activities/queries/create'; +import { GET_ACTIVITIES_BY_TARGETS, GET_ACTIVITY } from '@/activities/queries'; +import { CREATE_ACTIVITY_WITH_COMMENT } from '@/activities/queries/create'; import { GET_COMPANY } from '@/companies/queries'; import { PageDecorator, type PageDecoratorArgs, } from '~/testing/decorators/PageDecorator'; import { graphqlMocks } from '~/testing/graphqlMocks'; -import { mockedCommentThreads } from '~/testing/mock-data/comment-threads'; +import { mockedActivities } from '~/testing/mock-data/activities'; import { mockedCompaniesData } from '~/testing/mock-data/companies'; import { CompanyShow } from '../CompanyShow'; @@ -30,11 +27,11 @@ const meta: Meta = { msw: [ ...graphqlMocks, graphql.query( - getOperationName(GET_COMMENT_THREADS_BY_TARGETS) ?? '', + getOperationName(GET_ACTIVITIES_BY_TARGETS) ?? '', (req, res, ctx) => { return res( ctx.data({ - findManyCommentThreads: mockedCommentThreads, + findManyActivities: mockedActivities, }), ); }, @@ -82,25 +79,22 @@ export const EditNote: Story = { msw: [ ...meta.parameters?.msw, graphql.mutation( - getOperationName(CREATE_COMMENT_THREAD_WITH_COMMENT) ?? '', + getOperationName(CREATE_ACTIVITY_WITH_COMMENT) ?? '', (req, res, ctx) => { return res( ctx.data({ - createOneCommentThread: mockedCommentThreads[0], - }), - ); - }, - ), - graphql.query( - getOperationName(GET_COMMENT_THREAD) ?? '', - (req, res, ctx) => { - return res( - ctx.data({ - findManyCommentThreads: [mockedCommentThreads[0]], + createOneActivity: mockedActivities[0], }), ); }, ), + graphql.query(getOperationName(GET_ACTIVITY) ?? '', (req, res, ctx) => { + return res( + ctx.data({ + findManyActivitys: [mockedActivities[0]], + }), + ); + }), ], }, }; diff --git a/front/src/pages/people/People.tsx b/front/src/pages/people/People.tsx index 2cf805317..28a033809 100644 --- a/front/src/pages/people/People.tsx +++ b/front/src/pages/people/People.tsx @@ -4,7 +4,7 @@ import styled from '@emotion/styled'; import { GET_PEOPLE } from '@/people/queries'; import { PeopleTable } from '@/people/table/components/PeopleTable'; -import { TableActionBarButtonCreateCommentThreadPeople } from '@/people/table/components/TableActionBarButtonCreateCommentThreadPeople'; +import { TableActionBarButtonCreateActivityPeople } from '@/people/table/components/TableActionBarButtonCreateActivityPeople'; import { TableActionBarButtonDeletePeople } from '@/people/table/components/TableActionBarButtonDeletePeople'; import { IconUser } from '@/ui/icon'; import { WithTopBarContainer } from '@/ui/layout/components/WithTopBarContainer'; @@ -46,7 +46,7 @@ export function People() { - + diff --git a/front/src/testing/mock-data/comment-threads.ts b/front/src/testing/mock-data/activities.ts similarity index 77% rename from front/src/testing/mock-data/comment-threads.ts rename to front/src/testing/mock-data/activities.ts index b523d7d44..b2e71919d 100644 --- a/front/src/testing/mock-data/comment-threads.ts +++ b/front/src/testing/mock-data/activities.ts @@ -1,13 +1,13 @@ import { + Activity, + ActivityTarget, ActivityType, Comment, CommentableType, - CommentThread, - CommentThreadTarget, } from '~/generated/graphql'; -type MockedCommentThread = Pick< - CommentThread, +type MockedActivity = Pick< + Activity, | 'id' | 'createdAt' | 'updatedAt' @@ -25,21 +25,21 @@ type MockedCommentThread = Pick< displayName: string; }; comments: Array>; - commentThreadTargets: Array< + activityTargets: Array< Pick< - CommentThreadTarget, + ActivityTarget, | 'id' | '__typename' | 'createdAt' | 'updatedAt' - | 'commentableType' + | 'activityId' | 'commentableId' - | 'commentThreadId' - > & { commentThread: Pick } + | 'commentableType' + > & { activity: Pick } >; }; -export const mockedCommentThreads: Array = [ +export const mockedActivities: Array = [ { id: '89bb825c-171e-4bcc-9cf7-43448d6fb230', createdAt: '2023-04-26T10:12:42.33625+00:00', @@ -55,20 +55,20 @@ export const mockedCommentThreads: Array = [ }, authorId: '374fe3a5-df1e-4119-afe0-2a62a2ba481e', comments: [], - commentThreadTargets: [ + activityTargets: [ { id: '89bb825c-171e-4bcc-9cf7-43448d6fb300', createdAt: '2023-04-26T10:12:42.33625+00:00', updatedAt: '2023-04-26T10:23:42.33625+00:00', commentableType: CommentableType.Company, commentableId: '89bb825c-171e-4bcc-9cf7-43448d6fb278', // airbnb - commentThreadId: '89bb825c-171e-4bcc-9cf7-43448d6fb230', - commentThread: { + activityId: '89bb825c-171e-4bcc-9cf7-43448d6fb230', + activity: { id: '89bb825c-171e-4bcc-9cf7-43448d6fb230', createdAt: '2023-04-26T10:12:42.33625+00:00', updatedAt: '2023-04-26T10:23:42.33625+00:00', }, - __typename: 'CommentThreadTarget', + __typename: 'ActivityTarget', }, { id: '89bb825c-171e-4bcc-9cf7-43448d6fb301', @@ -76,16 +76,16 @@ export const mockedCommentThreads: Array = [ updatedAt: new Date().toISOString(), commentableType: CommentableType.Company, commentableId: 'b396e6b9-dc5c-4643-bcff-61b6cf7523ae', // aircall - commentThreadId: '89bb825c-171e-4bcc-9cf7-43448d6fb231', - commentThread: { + activityId: '89bb825c-171e-4bcc-9cf7-43448d6fb231', + activity: { id: '89bb825c-171e-4bcc-9cf7-43448d6fb231', createdAt: new Date().toISOString(), updatedAt: new Date().toISOString(), }, - __typename: 'CommentThreadTarget', + __typename: 'ActivityTarget', }, ], - __typename: 'CommentThread', + __typename: 'Activity', }, { id: '89bb825c-171e-4bcc-9cf7-43448d6fb278', @@ -102,20 +102,20 @@ export const mockedCommentThreads: Array = [ }, authorId: '374fe3a5-df1e-4119-afe0-2a62a2ba481e', comments: [], - commentThreadTargets: [ + activityTargets: [ { id: '89bb825c-171e-4bcc-9cf7-43448d6fb278', createdAt: '2023-04-26T10:12:42.33625+00:00', updatedAt: '2023-04-26T10:23:42.33625+00:00', commentableType: CommentableType.Person, commentableId: '7dfbc3f7-6e5e-4128-957e-8d86808cdf6b', // Alexandre - commentThreadId: '89bb825c-171e-4bcc-9cf7-43448d6fb278', - commentThread: { + activityId: '89bb825c-171e-4bcc-9cf7-43448d6fb278', + activity: { id: '89bb825c-171e-4bcc-9cf7-43448d6fb278', createdAt: '2023-04-26T10:12:42.33625+00:00', updatedAt: '2023-04-26T10:23:42.33625+00:00', }, - __typename: 'CommentThreadTarget', + __typename: 'ActivityTarget', }, { id: '89bb825c-171e-4bcc-9cf7-43448d6fb278', @@ -123,15 +123,15 @@ export const mockedCommentThreads: Array = [ updatedAt: new Date().toISOString(), commentableType: CommentableType.Person, commentableId: '7dfbc3f7-6e5e-4128-957e-8d86808cdf6d', // Jean d'Eau - commentThreadId: '89bb825c-171e-4bcc-9cf7-43448d6fb278', - commentThread: { + activityId: '89bb825c-171e-4bcc-9cf7-43448d6fb278', + activity: { id: '89bb825c-171e-4bcc-9cf7-43448d6fb278', createdAt: new Date().toISOString(), updatedAt: new Date().toISOString(), }, - __typename: 'CommentThreadTarget', + __typename: 'ActivityTarget', }, ], - __typename: 'CommentThread', + __typename: 'Activity', }, ]; diff --git a/front/src/testing/mock-data/companies.ts b/front/src/testing/mock-data/companies.ts index 5dffe59bf..e881f452e 100644 --- a/front/src/testing/mock-data/companies.ts +++ b/front/src/testing/mock-data/companies.ts @@ -10,7 +10,7 @@ type MockedCompany = Pick< | 'address' | 'employees' | 'linkedinUrl' - | '_commentThreadCount' + | '_activityCount' > & { accountOwner: Pick< User, @@ -33,7 +33,7 @@ export const mockedCompaniesData: Array = [ address: '17 rue de clignancourt', employees: 12, linkedinUrl: 'https://www.linkedin.com/company/airbnb/', - _commentThreadCount: 1, + _activityCount: 1, accountOwner: { email: 'charles@test.com', displayName: 'Charles Test', @@ -53,7 +53,7 @@ export const mockedCompaniesData: Array = [ address: '', employees: 1, linkedinUrl: 'https://www.linkedin.com/company/aircall/', - _commentThreadCount: 1, + _activityCount: 1, accountOwner: null, __typename: 'Company', }, @@ -65,7 +65,7 @@ export const mockedCompaniesData: Array = [ address: '', employees: 1, linkedinUrl: 'https://www.linkedin.com/company/algolia/', - _commentThreadCount: 1, + _activityCount: 1, accountOwner: null, __typename: 'Company', }, @@ -77,7 +77,7 @@ export const mockedCompaniesData: Array = [ address: '', employees: 10, linkedinUrl: 'https://www.linkedin.com/company/apple/', - _commentThreadCount: 0, + _activityCount: 0, accountOwner: null, __typename: 'Company', }, @@ -89,7 +89,7 @@ export const mockedCompaniesData: Array = [ address: '10 rue de la Paix', employees: 1, linkedinUrl: 'https://www.linkedin.com/company/qonto/', - _commentThreadCount: 2, + _activityCount: 2, accountOwner: null, __typename: 'Company', }, @@ -101,7 +101,7 @@ export const mockedCompaniesData: Array = [ address: '', employees: 1, linkedinUrl: 'https://www.linkedin.com/company/facebook/', - _commentThreadCount: 13, + _activityCount: 13, accountOwner: null, __typename: 'Company', }, @@ -113,7 +113,7 @@ export const mockedCompaniesData: Array = [ address: '', employees: 1, linkedinUrl: 'https://www.linkedin.com/company/sequoia/', - _commentThreadCount: 1, + _activityCount: 1, accountOwner: null, __typename: 'Company', }, diff --git a/front/src/testing/mock-data/people.ts b/front/src/testing/mock-data/people.ts index ba1b96984..9cedd4fde 100644 --- a/front/src/testing/mock-data/people.ts +++ b/front/src/testing/mock-data/people.ts @@ -17,7 +17,7 @@ type MockedPerson = RequiredAndNotNull< | '__typename' | 'phone' | 'city' - | '_commentThreadCount' + | '_activityCount' | 'createdAt' > & { company: Pick; @@ -41,7 +41,7 @@ export const mockedPeopleData: MockedPerson[] = [ __typename: 'Company', }, phone: '06 12 34 56 78', - _commentThreadCount: 1, + _activityCount: 1, createdAt: '2023-04-20T13:20:09.158312+00:00', city: 'Paris', @@ -62,7 +62,7 @@ export const mockedPeopleData: MockedPerson[] = [ __typename: 'Company', }, phone: '06 12 34 56 78', - _commentThreadCount: 1, + _activityCount: 1, createdAt: '2023-04-20T13:20:09.158312+00:00', city: 'Paris', @@ -83,7 +83,7 @@ export const mockedPeopleData: MockedPerson[] = [ __typename: 'Company', }, phone: '06 12 34 56 78', - _commentThreadCount: 1, + _activityCount: 1, createdAt: '2023-04-20T13:20:09.158312+00:00', city: 'Paris', @@ -104,7 +104,7 @@ export const mockedPeopleData: MockedPerson[] = [ __typename: 'Company', }, phone: '06 12 34 56 78', - _commentThreadCount: 2, + _activityCount: 2, createdAt: '2023-04-20T13:20:09.158312+00:00', city: 'Paris', diff --git a/server/src/ability/ability.factory.ts b/server/src/ability/ability.factory.ts index 6b927f328..bd6ef0738 100644 --- a/server/src/ability/ability.factory.ts +++ b/server/src/ability/ability.factory.ts @@ -3,7 +3,8 @@ import { Injectable } from '@nestjs/common'; import { PureAbility, AbilityBuilder } from '@casl/ability'; import { createPrismaAbility, PrismaQuery, Subjects } from '@casl/prisma'; import { - CommentThread, + Attachment, + Activity, Company, Comment, Person, @@ -11,11 +12,10 @@ import { User, Workspace, WorkspaceMember, - CommentThreadTarget, + ActivityTarget, Pipeline, PipelineStage, PipelineProgress, - Attachment, UserSettings, ViewField, } from '@prisma/client'; @@ -29,9 +29,9 @@ type SubjectsAbility = Subjects<{ Company: Company; Person: Person; RefreshToken: RefreshToken; - CommentThread: CommentThread; + Activity: Activity; Comment: Comment; - CommentThreadTarget: CommentThreadTarget; + ActivityTarget: ActivityTarget; Pipeline: Pipeline; PipelineStage: PipelineStage; PipelineProgress: PipelineProgress; @@ -86,11 +86,11 @@ export class AbilityFactory { // RefreshToken cannot(AbilityAction.Manage, 'RefreshToken'); - // CommentThread - can(AbilityAction.Read, 'CommentThread', { workspaceId: workspace.id }); - can(AbilityAction.Create, 'CommentThread'); - can(AbilityAction.Update, 'CommentThread', { workspaceId: workspace.id }); - can(AbilityAction.Delete, 'CommentThread', { workspaceId: workspace.id }); + // Activity + can(AbilityAction.Read, 'Activity', { workspaceId: workspace.id }); + can(AbilityAction.Create, 'Activity'); + can(AbilityAction.Update, 'Activity', { workspaceId: workspace.id }); + can(AbilityAction.Delete, 'Activity', { workspaceId: workspace.id }); // Comment can(AbilityAction.Read, 'Comment', { workspaceId: workspace.id }); @@ -104,9 +104,9 @@ export class AbilityFactory { authorId: user.id, }); - // CommentThreadTarget - can(AbilityAction.Read, 'CommentThreadTarget'); - can(AbilityAction.Create, 'CommentThreadTarget'); + // ActivityTarget + can(AbilityAction.Read, 'ActivityTarget'); + can(AbilityAction.Create, 'ActivityTarget'); // Attachment can(AbilityAction.Read, 'Attachment', { workspaceId: workspace.id }); diff --git a/server/src/ability/ability.module.ts b/server/src/ability/ability.module.ts index 8b3c12c97..7ed68238c 100644 --- a/server/src/ability/ability.module.ts +++ b/server/src/ability/ability.module.ts @@ -46,12 +46,12 @@ import { DeleteRefreshTokenAbilityHandler, } from './handlers/refresh-token.ability-handler'; import { - ManageCommentThreadAbilityHandler, - ReadCommentThreadAbilityHandler, - CreateCommentThreadAbilityHandler, - UpdateCommentThreadAbilityHandler, - DeleteCommentThreadAbilityHandler, -} from './handlers/comment-thread.ability-handler'; + ManageActivityAbilityHandler, + ReadActivityAbilityHandler, + CreateActivityAbilityHandler, + UpdateActivityAbilityHandler, + DeleteActivityAbilityHandler, +} from './handlers/activity.ability-handler'; import { ManageCommentAbilityHandler, ReadCommentAbilityHandler, @@ -60,12 +60,12 @@ import { DeleteCommentAbilityHandler, } from './handlers/comment.ability-handler'; import { - ManageCommentThreadTargetAbilityHandler, - ReadCommentThreadTargetAbilityHandler, - CreateCommentThreadTargetAbilityHandler, - UpdateCommentThreadTargetAbilityHandler, - DeleteCommentThreadTargetAbilityHandler, -} from './handlers/comment-thread-target.ability-handler'; + ManageActivityTargetAbilityHandler, + ReadActivityTargetAbilityHandler, + CreateActivityTargetAbilityHandler, + UpdateActivityTargetAbilityHandler, + DeleteActivityTargetAbilityHandler, +} from './handlers/activity-target.ability-handler'; import { ManagePipelineAbilityHandler, ReadPipelineAbilityHandler, @@ -140,24 +140,24 @@ import { CreateRefreshTokenAbilityHandler, UpdateRefreshTokenAbilityHandler, DeleteRefreshTokenAbilityHandler, - // CommentThread - ManageCommentThreadAbilityHandler, - ReadCommentThreadAbilityHandler, - CreateCommentThreadAbilityHandler, - UpdateCommentThreadAbilityHandler, - DeleteCommentThreadAbilityHandler, + // Activity + ManageActivityAbilityHandler, + ReadActivityAbilityHandler, + CreateActivityAbilityHandler, + UpdateActivityAbilityHandler, + DeleteActivityAbilityHandler, // Comment ManageCommentAbilityHandler, ReadCommentAbilityHandler, CreateCommentAbilityHandler, UpdateCommentAbilityHandler, DeleteCommentAbilityHandler, - // CommentThreadTarget - ManageCommentThreadTargetAbilityHandler, - ReadCommentThreadTargetAbilityHandler, - CreateCommentThreadTargetAbilityHandler, - UpdateCommentThreadTargetAbilityHandler, - DeleteCommentThreadTargetAbilityHandler, + // ActivityTarget + ManageActivityTargetAbilityHandler, + ReadActivityTargetAbilityHandler, + CreateActivityTargetAbilityHandler, + UpdateActivityTargetAbilityHandler, + DeleteActivityTargetAbilityHandler, //Attachment ManageAttachmentAbilityHandler, ReadAttachmentAbilityHandler, @@ -224,24 +224,24 @@ import { CreateRefreshTokenAbilityHandler, UpdateRefreshTokenAbilityHandler, DeleteRefreshTokenAbilityHandler, - // CommentThread - ManageCommentThreadAbilityHandler, - ReadCommentThreadAbilityHandler, - CreateCommentThreadAbilityHandler, - UpdateCommentThreadAbilityHandler, - DeleteCommentThreadAbilityHandler, + // Activity + ManageActivityAbilityHandler, + ReadActivityAbilityHandler, + CreateActivityAbilityHandler, + UpdateActivityAbilityHandler, + DeleteActivityAbilityHandler, // Comment ManageCommentAbilityHandler, ReadCommentAbilityHandler, CreateCommentAbilityHandler, UpdateCommentAbilityHandler, DeleteCommentAbilityHandler, - // CommentThreadTarget - ManageCommentThreadTargetAbilityHandler, - ReadCommentThreadTargetAbilityHandler, - CreateCommentThreadTargetAbilityHandler, - UpdateCommentThreadTargetAbilityHandler, - DeleteCommentThreadTargetAbilityHandler, + // ActivityTarget + ManageActivityTargetAbilityHandler, + ReadActivityTargetAbilityHandler, + CreateActivityTargetAbilityHandler, + UpdateActivityTargetAbilityHandler, + DeleteActivityTargetAbilityHandler, //Attachment ManageAttachmentAbilityHandler, ReadAttachmentAbilityHandler, diff --git a/server/src/ability/handlers/activity-target.ability-handler.ts b/server/src/ability/handlers/activity-target.ability-handler.ts new file mode 100644 index 000000000..633c7ac15 --- /dev/null +++ b/server/src/ability/handlers/activity-target.ability-handler.ts @@ -0,0 +1,79 @@ +import { + ExecutionContext, + Injectable, + NotFoundException, +} from '@nestjs/common'; +import { GqlExecutionContext } from '@nestjs/graphql'; + +import { subject } from '@casl/ability'; + +import { IAbilityHandler } from 'src/ability/interfaces/ability-handler.interface'; + +import { PrismaService } from 'src/database/prisma.service'; +import { AbilityAction } from 'src/ability/ability.action'; +import { AppAbility } from 'src/ability/ability.factory'; +import { assert } from 'src/utils/assert'; +import { ActivityTargetWhereInput } from 'src/core/@generated/activity-target/activity-target-where.input'; + +class ActivityTargetArgs { + where?: ActivityTargetWhereInput; +} + +@Injectable() +export class ManageActivityTargetAbilityHandler implements IAbilityHandler { + async handle(ability: AppAbility) { + return ability.can(AbilityAction.Manage, 'ActivityTarget'); + } +} + +@Injectable() +export class ReadActivityTargetAbilityHandler implements IAbilityHandler { + handle(ability: AppAbility) { + return ability.can(AbilityAction.Read, 'ActivityTarget'); + } +} + +@Injectable() +export class CreateActivityTargetAbilityHandler implements IAbilityHandler { + handle(ability: AppAbility) { + return ability.can(AbilityAction.Create, 'ActivityTarget'); + } +} + +@Injectable() +export class UpdateActivityTargetAbilityHandler implements IAbilityHandler { + constructor(private readonly prismaService: PrismaService) {} + + async handle(ability: AppAbility, context: ExecutionContext) { + const gqlContext = GqlExecutionContext.create(context); + const args = gqlContext.getArgs(); + const ActivityTarget = await this.prismaService.client.activityTarget.findFirst({ + where: args.where, + }); + assert(ActivityTarget, '', NotFoundException); + + return ability.can( + AbilityAction.Update, + subject('ActivityTarget', ActivityTarget), + ); + } +} + +@Injectable() +export class DeleteActivityTargetAbilityHandler implements IAbilityHandler { + constructor(private readonly prismaService: PrismaService) {} + + async handle(ability: AppAbility, context: ExecutionContext) { + const gqlContext = GqlExecutionContext.create(context); + const args = gqlContext.getArgs(); + const ActivityTarget = await this.prismaService.client.activityTarget.findFirst({ + where: args.where, + }); + assert(ActivityTarget, '', NotFoundException); + + return ability.can( + AbilityAction.Delete, + subject('ActivityTarget', ActivityTarget), + ); + } +} diff --git a/server/src/ability/handlers/activity.ability-handler.ts b/server/src/ability/handlers/activity.ability-handler.ts new file mode 100644 index 000000000..c161af2fa --- /dev/null +++ b/server/src/ability/handlers/activity.ability-handler.ts @@ -0,0 +1,73 @@ +import { + ExecutionContext, + Injectable, + NotFoundException, +} from '@nestjs/common'; +import { GqlExecutionContext } from '@nestjs/graphql'; + +import { subject } from '@casl/ability'; + +import { IAbilityHandler } from 'src/ability/interfaces/ability-handler.interface'; + +import { PrismaService } from 'src/database/prisma.service'; +import { AbilityAction } from 'src/ability/ability.action'; +import { AppAbility } from 'src/ability/ability.factory'; +import { assert } from 'src/utils/assert'; +import { ActivityWhereInput } from 'src/core/@generated/activity/activity-where.input'; + +class ActivityArgs { + where?: ActivityWhereInput; +} + +@Injectable() +export class ManageActivityAbilityHandler implements IAbilityHandler { + async handle(ability: AppAbility) { + return ability.can(AbilityAction.Manage, 'Activity'); + } +} + +@Injectable() +export class ReadActivityAbilityHandler implements IAbilityHandler { + handle(ability: AppAbility) { + return ability.can(AbilityAction.Read, 'Activity'); + } +} + +@Injectable() +export class CreateActivityAbilityHandler implements IAbilityHandler { + handle(ability: AppAbility) { + return ability.can(AbilityAction.Create, 'Activity'); + } +} + +@Injectable() +export class UpdateActivityAbilityHandler implements IAbilityHandler { + constructor(private readonly prismaService: PrismaService) {} + + async handle(ability: AppAbility, context: ExecutionContext) { + const gqlContext = GqlExecutionContext.create(context); + const args = gqlContext.getArgs(); + const Activity = await this.prismaService.client.activity.findFirst({ + where: args.where, + }); + assert(Activity, '', NotFoundException); + + return ability.can(AbilityAction.Update, subject('Activity', Activity)); + } +} + +@Injectable() +export class DeleteActivityAbilityHandler implements IAbilityHandler { + constructor(private readonly prismaService: PrismaService) {} + + async handle(ability: AppAbility, context: ExecutionContext) { + const gqlContext = GqlExecutionContext.create(context); + const args = gqlContext.getArgs(); + const Activity = await this.prismaService.client.activity.findFirst({ + where: args.where, + }); + assert(Activity, '', NotFoundException); + + return ability.can(AbilityAction.Delete, subject('Activity', Activity)); + } +} diff --git a/server/src/ability/handlers/attachment.ability-handler.ts b/server/src/ability/handlers/attachment.ability-handler.ts index d46dc08c2..6c2d33fd8 100644 --- a/server/src/ability/handlers/attachment.ability-handler.ts +++ b/server/src/ability/handlers/attachment.ability-handler.ts @@ -42,16 +42,12 @@ export class CreateAttachmentAbilityHandler implements IAbilityHandler { const args = gqlContext.getArgs(); assert(args.activityId, '', ForbiddenException); - const activity = await this.prismaService.client.commentThread.findUnique({ + const activity = await this.prismaService.client.activity.findUnique({ where: { id: args.activityId }, - include: { workspace: true }, }); assert(activity, '', NotFoundException); - return ability.can( - AbilityAction.Update, - subject('Workspace', activity.workspace), - ); + return ability.can(AbilityAction.Update, subject('Activity', activity)); } } diff --git a/server/src/ability/handlers/comment-thread-target.ability-handler.ts b/server/src/ability/handlers/comment-thread-target.ability-handler.ts deleted file mode 100644 index 24110637d..000000000 --- a/server/src/ability/handlers/comment-thread-target.ability-handler.ts +++ /dev/null @@ -1,118 +0,0 @@ -import { - ExecutionContext, - Injectable, - NotFoundException, -} from '@nestjs/common'; -import { GqlExecutionContext } from '@nestjs/graphql'; - -import { subject } from '@casl/ability'; - -import { IAbilityHandler } from 'src/ability/interfaces/ability-handler.interface'; - -import { PrismaService } from 'src/database/prisma.service'; -import { AbilityAction } from 'src/ability/ability.action'; -import { AppAbility } from 'src/ability/ability.factory'; -import { CommentThreadTargetWhereInput } from 'src/core/@generated/comment-thread-target/comment-thread-target-where.input'; -import { relationAbilityChecker } from 'src/ability/ability.util'; -import { assert } from 'src/utils/assert'; - -class CommentThreadTargetArgs { - where?: CommentThreadTargetWhereInput; - [key: string]: any; -} - -@Injectable() -export class ManageCommentThreadTargetAbilityHandler - implements IAbilityHandler -{ - async handle(ability: AppAbility) { - return ability.can(AbilityAction.Manage, 'CommentThreadTarget'); - } -} - -@Injectable() -export class ReadCommentThreadTargetAbilityHandler implements IAbilityHandler { - handle(ability: AppAbility) { - return ability.can(AbilityAction.Read, 'CommentThreadTarget'); - } -} - -@Injectable() -export class CreateCommentThreadTargetAbilityHandler - implements IAbilityHandler -{ - constructor(private readonly prismaService: PrismaService) {} - - async handle(ability: AppAbility, context: ExecutionContext) { - const gqlContext = GqlExecutionContext.create(context); - const args = gqlContext.getArgs(); - - const allowed = await relationAbilityChecker( - 'CommentThreadTarget', - ability, - this.prismaService.client, - args, - ); - - if (!allowed) { - return false; - } - - return ability.can(AbilityAction.Create, 'CommentThreadTarget'); - } -} - -@Injectable() -export class UpdateCommentThreadTargetAbilityHandler - implements IAbilityHandler -{ - constructor(private readonly prismaService: PrismaService) {} - - async handle(ability: AppAbility, context: ExecutionContext) { - const gqlContext = GqlExecutionContext.create(context); - const args = gqlContext.getArgs(); - const commentThreadTarget = - await this.prismaService.client.commentThreadTarget.findFirst({ - where: args.where, - }); - assert(commentThreadTarget, '', NotFoundException); - - const allowed = await relationAbilityChecker( - 'CommentThreadTarget', - ability, - this.prismaService.client, - args, - ); - - if (!allowed) { - return false; - } - - return ability.can( - AbilityAction.Update, - subject('CommentThreadTarget', commentThreadTarget), - ); - } -} - -@Injectable() -export class DeleteCommentThreadTargetAbilityHandler - implements IAbilityHandler -{ - constructor(private readonly prismaService: PrismaService) {} - - async handle(ability: AppAbility, context: ExecutionContext) { - const gqlContext = GqlExecutionContext.create(context); - const args = gqlContext.getArgs(); - const commentThreadTarget = - await this.prismaService.client.commentThreadTarget.findFirst({ - where: args.where, - }); - assert(commentThreadTarget, '', NotFoundException); - - return ability.can( - AbilityAction.Delete, - subject('CommentThreadTarget', commentThreadTarget), - ); - } -} diff --git a/server/src/ability/handlers/comment-thread.ability-handler.ts b/server/src/ability/handlers/comment-thread.ability-handler.ts deleted file mode 100644 index e9b3cd8e9..000000000 --- a/server/src/ability/handlers/comment-thread.ability-handler.ts +++ /dev/null @@ -1,110 +0,0 @@ -import { - ExecutionContext, - Injectable, - NotFoundException, -} from '@nestjs/common'; -import { GqlExecutionContext } from '@nestjs/graphql'; - -import { subject } from '@casl/ability'; - -import { IAbilityHandler } from 'src/ability/interfaces/ability-handler.interface'; - -import { PrismaService } from 'src/database/prisma.service'; -import { AbilityAction } from 'src/ability/ability.action'; -import { AppAbility } from 'src/ability/ability.factory'; -import { CommentThreadWhereInput } from 'src/core/@generated/comment-thread/comment-thread-where.input'; -import { relationAbilityChecker } from 'src/ability/ability.util'; -import { assert } from 'src/utils/assert'; - -class CommentThreadArgs { - where?: CommentThreadWhereInput; - [key: string]: any; -} - -@Injectable() -export class ManageCommentThreadAbilityHandler implements IAbilityHandler { - async handle(ability: AppAbility) { - return ability.can(AbilityAction.Manage, 'CommentThread'); - } -} - -@Injectable() -export class ReadCommentThreadAbilityHandler implements IAbilityHandler { - handle(ability: AppAbility) { - return ability.can(AbilityAction.Read, 'CommentThread'); - } -} - -@Injectable() -export class CreateCommentThreadAbilityHandler implements IAbilityHandler { - constructor(private readonly prismaService: PrismaService) {} - - async handle(ability: AppAbility, context: ExecutionContext) { - const gqlContext = GqlExecutionContext.create(context); - const args = gqlContext.getArgs(); - - const allowed = await relationAbilityChecker( - 'CommentThread', - ability, - this.prismaService.client, - args, - ); - - if (!allowed) { - return false; - } - - return ability.can(AbilityAction.Create, 'CommentThread'); - } -} - -@Injectable() -export class UpdateCommentThreadAbilityHandler implements IAbilityHandler { - constructor(private readonly prismaService: PrismaService) {} - - async handle(ability: AppAbility, context: ExecutionContext) { - const gqlContext = GqlExecutionContext.create(context); - const args = gqlContext.getArgs(); - const commentThread = - await this.prismaService.client.commentThread.findFirst({ - where: args.where, - }); - assert(commentThread, '', NotFoundException); - - const allowed = await relationAbilityChecker( - 'CommentThread', - ability, - this.prismaService.client, - args, - ); - - if (!allowed) { - return false; - } - - return ability.can( - AbilityAction.Update, - subject('CommentThread', commentThread), - ); - } -} - -@Injectable() -export class DeleteCommentThreadAbilityHandler implements IAbilityHandler { - constructor(private readonly prismaService: PrismaService) {} - - async handle(ability: AppAbility, context: ExecutionContext) { - const gqlContext = GqlExecutionContext.create(context); - const args = gqlContext.getArgs(); - const commentThread = - await this.prismaService.client.commentThread.findFirst({ - where: args.where, - }); - assert(commentThread, '', NotFoundException); - - return ability.can( - AbilityAction.Delete, - subject('CommentThread', commentThread), - ); - } -} diff --git a/server/src/core/activity/activity.module.ts b/server/src/core/activity/activity.module.ts new file mode 100644 index 000000000..2c161f022 --- /dev/null +++ b/server/src/core/activity/activity.module.ts @@ -0,0 +1,11 @@ +import { Module } from '@nestjs/common'; + +import { ActivityResolver } from './resolvers/activity.resolver'; +import { ActivityService } from './services/activity.service'; +import { ActivityTargetService } from './services/activity-target.service'; + +@Module({ + providers: [ActivityResolver, ActivityService, ActivityTargetService], + exports: [ActivityService, ActivityTargetService], +}) +export class ActivityModule {} diff --git a/server/src/core/comment/resolvers/comment-thread.resolver.spec.ts b/server/src/core/activity/resolvers/activity.resolver.spec.ts similarity index 55% rename from server/src/core/comment/resolvers/comment-thread.resolver.spec.ts rename to server/src/core/activity/resolvers/activity.resolver.spec.ts index 12f11fd85..63bf6ebb7 100644 --- a/server/src/core/comment/resolvers/comment-thread.resolver.spec.ts +++ b/server/src/core/activity/resolvers/activity.resolver.spec.ts @@ -1,19 +1,19 @@ import { Test, TestingModule } from '@nestjs/testing'; -import { CommentThreadService } from 'src/core/comment/services/comment-thread.service'; +import { ActivityService } from 'src/core/activity/services/activity.service'; import { AbilityFactory } from 'src/ability/ability.factory'; -import { CommentThreadResolver } from './comment-thread.resolver'; +import { ActivityResolver } from './activity.resolver'; -describe('CommentThreadResolver', () => { - let resolver: CommentThreadResolver; +describe('ActivityResolver', () => { + let resolver: ActivityResolver; beforeEach(async () => { const module: TestingModule = await Test.createTestingModule({ providers: [ - CommentThreadResolver, + ActivityResolver, { - provide: CommentThreadService, + provide: ActivityService, useValue: {}, }, { @@ -23,7 +23,7 @@ describe('CommentThreadResolver', () => { ], }).compile(); - resolver = module.get(CommentThreadResolver); + resolver = module.get(ActivityResolver); }); it('should be defined', () => { diff --git a/server/src/core/activity/resolvers/activity.resolver.ts b/server/src/core/activity/resolvers/activity.resolver.ts new file mode 100644 index 000000000..231df7590 --- /dev/null +++ b/server/src/core/activity/resolvers/activity.resolver.ts @@ -0,0 +1,156 @@ +import { Resolver, Args, Mutation, Query } from '@nestjs/graphql'; +import { UseGuards } from '@nestjs/common'; + +import { accessibleBy } from '@casl/prisma'; +import { Prisma } from '@prisma/client'; + +import { JwtAuthGuard } from 'src/guards/jwt.auth.guard'; +import { AuthWorkspace } from 'src/decorators/auth-workspace.decorator'; +import { + PrismaSelector, + PrismaSelect, +} from 'src/decorators/prisma-select.decorator'; +import { AbilityGuard } from 'src/guards/ability.guard'; +import { CheckAbilities } from 'src/decorators/check-abilities.decorator'; +import { + CreateActivityAbilityHandler, + DeleteActivityAbilityHandler, + ReadActivityAbilityHandler, + UpdateActivityAbilityHandler, +} from 'src/ability/handlers/activity.ability-handler'; +import { UserAbility } from 'src/decorators/user-ability.decorator'; +import { AppAbility } from 'src/ability/ability.factory'; +import { AffectedRows } from 'src/core/@generated/prisma/affected-rows.output'; +import { Activity } from 'src/core/@generated/activity/activity.model'; +import { ActivityService } from 'src/core/activity/services/activity.service'; +import { CreateOneActivityArgs } from 'src/core/@generated/activity/create-one-activity.args'; +import { Workspace } from 'src/core/@generated/workspace/workspace.model'; +import { UpdateOneActivityArgs } from 'src/core/@generated/activity/update-one-activity.args'; +import { FindManyActivityArgs } from 'src/core/@generated/activity/find-many-activity.args'; +import { DeleteManyActivityArgs } from 'src/core/@generated/activity/delete-many-activity.args'; + +@UseGuards(JwtAuthGuard) +@Resolver(() => Activity) +export class ActivityResolver { + constructor(private readonly activityService: ActivityService) {} + + @Mutation(() => Activity, { + nullable: false, + }) + @UseGuards(AbilityGuard) + @CheckAbilities(CreateActivityAbilityHandler) + async createOneActivity( + @Args() args: CreateOneActivityArgs, + @AuthWorkspace() workspace: Workspace, + @PrismaSelector({ modelName: 'Activity' }) + prismaSelect: PrismaSelect<'Activity'>, + ): Promise> { + const createdActivity = await this.activityService.create({ + data: { + ...args.data, + ...{ workspace: { connect: { id: workspace.id } } }, + activityTargets: args.data?.activityTargets?.createMany + ? { + createMany: { + data: args.data.activityTargets.createMany.data.map( + (target) => ({ ...target, workspaceId: workspace.id }), + ), + }, + } + : undefined, + }, + select: prismaSelect.value, + } as Prisma.ActivityCreateArgs); + + return createdActivity; + } + + @Mutation(() => Activity, { + nullable: false, + }) + @UseGuards(AbilityGuard) + @CheckAbilities(UpdateActivityAbilityHandler) + async updateOneActivity( + @Args() args: UpdateOneActivityArgs, + @AuthWorkspace() workspace: Workspace, + @PrismaSelector({ modelName: 'Activity' }) + prismaSelect: PrismaSelect<'Activity'>, + ): Promise> { + // TODO: Do a proper check with recursion testing on args in a more generic place + for (const key in args.data) { + if (args.data[key]) { + for (const subKey in args.data[key]) { + if (JSON.stringify(args.data[key][subKey]) === '{}') { + delete args.data[key][subKey]; + } + } + } + + if (JSON.stringify(args.data[key]) === '{}') { + delete args.data[key]; + } + } + const updatedActivity = await this.activityService.update({ + where: args.where, + data: { + ...args.data, + activityTargets: args.data?.activityTargets + ? { + createMany: args.data.activityTargets.createMany + ? { + data: args.data.activityTargets.createMany.data.map( + (target) => ({ + ...target, + workspaceId: workspace.id, + }), + ), + } + : undefined, + deleteMany: args.data.activityTargets.deleteMany ?? undefined, + } + : undefined, + }, + select: prismaSelect.value, + } as Prisma.ActivityUpdateArgs); + + return updatedActivity; + } + + @Query(() => [Activity]) + @UseGuards(AbilityGuard) + @CheckAbilities(ReadActivityAbilityHandler) + async findManyActivities( + @Args() args: FindManyActivityArgs, + @UserAbility() ability: AppAbility, + @PrismaSelector({ modelName: 'Activity' }) + prismaSelect: PrismaSelect<'Activity'>, + ): Promise[]> { + const result = await this.activityService.findMany({ + where: { + ...args.where, + AND: [accessibleBy(ability).Activity], + }, + orderBy: args.orderBy, + cursor: args.cursor, + take: args.take, + skip: args.skip, + distinct: args.distinct, + select: prismaSelect.value, + }); + + return result; + } + + @Mutation(() => AffectedRows, { + nullable: false, + }) + @UseGuards(AbilityGuard) + @CheckAbilities(DeleteActivityAbilityHandler) + async deleteManyActivities( + @Args() args: DeleteManyActivityArgs, + ): Promise { + return this.activityService.deleteMany({ + where: args.where, + }); + } +} diff --git a/server/src/core/comment/services/comment-thread-target.service.spec.ts b/server/src/core/activity/services/activity-target.service.spec.ts similarity index 63% rename from server/src/core/comment/services/comment-thread-target.service.spec.ts rename to server/src/core/activity/services/activity-target.service.spec.ts index 57ecf929e..cc18cd670 100644 --- a/server/src/core/comment/services/comment-thread-target.service.spec.ts +++ b/server/src/core/activity/services/activity-target.service.spec.ts @@ -3,15 +3,15 @@ import { Test, TestingModule } from '@nestjs/testing'; import { PrismaService } from 'src/database/prisma.service'; import { prismaMock } from 'src/database/client-mock/jest-prisma-singleton'; -import { CommentThreadTargetService } from './comment-thread-target.service'; +import { ActivityTargetService } from './activity-target.service'; -describe('CommentThreadTargetService', () => { - let service: CommentThreadTargetService; +describe('ActivityTargetService', () => { + let service: ActivityTargetService; beforeEach(async () => { const module: TestingModule = await Test.createTestingModule({ providers: [ - CommentThreadTargetService, + ActivityTargetService, { provide: PrismaService, useValue: prismaMock, @@ -19,9 +19,7 @@ describe('CommentThreadTargetService', () => { ], }).compile(); - service = module.get( - CommentThreadTargetService, - ); + service = module.get(ActivityTargetService); }); it('should be defined', () => { diff --git a/server/src/core/activity/services/activity-target.service.ts b/server/src/core/activity/services/activity-target.service.ts new file mode 100644 index 000000000..8c9398d54 --- /dev/null +++ b/server/src/core/activity/services/activity-target.service.ts @@ -0,0 +1,40 @@ +import { Injectable } from '@nestjs/common'; + +import { PrismaService } from 'src/database/prisma.service'; + +@Injectable() +export class ActivityTargetService { + constructor(private readonly prismaService: PrismaService) {} + + // Find + findFirst = this.prismaService.client.activityTarget.findFirst; + findFirstOrThrow = this.prismaService.client.activityTarget.findFirstOrThrow; + + findUnique = this.prismaService.client.activityTarget.findUnique; + findUniqueOrThrow = + this.prismaService.client.activityTarget.findUniqueOrThrow; + + findMany = this.prismaService.client.activityTarget.findMany; + + // Create + create = this.prismaService.client.activityTarget.create; + createMany = this.prismaService.client.activityTarget.createMany; + + // Update + update = this.prismaService.client.activityTarget.update; + upsert = this.prismaService.client.activityTarget.upsert; + updateMany = this.prismaService.client.activityTarget.updateMany; + + // Delete + delete = this.prismaService.client.activityTarget.delete; + deleteMany = this.prismaService.client.activityTarget.deleteMany; + + // Aggregate + aggregate = this.prismaService.client.activityTarget.aggregate; + + // Count + count = this.prismaService.client.activityTarget.count; + + // GroupBy + groupBy = this.prismaService.client.activityTarget.groupBy; +} diff --git a/server/src/core/comment/services/comment-thread.service.spec.ts b/server/src/core/activity/services/activity.service.spec.ts similarity index 67% rename from server/src/core/comment/services/comment-thread.service.spec.ts rename to server/src/core/activity/services/activity.service.spec.ts index f65fb76aa..5a58ece2f 100644 --- a/server/src/core/comment/services/comment-thread.service.spec.ts +++ b/server/src/core/activity/services/activity.service.spec.ts @@ -3,15 +3,15 @@ import { Test, TestingModule } from '@nestjs/testing'; import { PrismaService } from 'src/database/prisma.service'; import { prismaMock } from 'src/database/client-mock/jest-prisma-singleton'; -import { CommentThreadService } from './comment-thread.service'; +import { ActivityService } from './activity.service'; -describe('CommentThreadService', () => { - let service: CommentThreadService; +describe('ActivityService', () => { + let service: ActivityService; beforeEach(async () => { const module: TestingModule = await Test.createTestingModule({ providers: [ - CommentThreadService, + ActivityService, { provide: PrismaService, useValue: prismaMock, @@ -19,7 +19,7 @@ describe('CommentThreadService', () => { ], }).compile(); - service = module.get(CommentThreadService); + service = module.get(ActivityService); }); it('should be defined', () => { diff --git a/server/src/core/activity/services/activity.service.ts b/server/src/core/activity/services/activity.service.ts new file mode 100644 index 000000000..ce22974b0 --- /dev/null +++ b/server/src/core/activity/services/activity.service.ts @@ -0,0 +1,39 @@ +import { Injectable } from '@nestjs/common'; + +import { PrismaService } from 'src/database/prisma.service'; + +@Injectable() +export class ActivityService { + constructor(private readonly prismaService: PrismaService) {} + + // Find + findFirst = this.prismaService.client.activity.findFirst; + findFirstOrThrow = this.prismaService.client.activity.findFirstOrThrow; + + findUnique = this.prismaService.client.activity.findUnique; + findUniqueOrThrow = this.prismaService.client.activity.findUniqueOrThrow; + + findMany = this.prismaService.client.activity.findMany; + + // Create + create = this.prismaService.client.activity.create; + createMany = this.prismaService.client.activity.createMany; + + // Update + update = this.prismaService.client.activity.update; + upsert = this.prismaService.client.activity.upsert; + updateMany = this.prismaService.client.activity.updateMany; + + // Delete + delete = this.prismaService.client.activity.delete; + deleteMany = this.prismaService.client.activity.deleteMany; + + // Aggregate + aggregate = this.prismaService.client.activity.aggregate; + + // Count + count = this.prismaService.client.activity.count; + + // GroupBy + groupBy = this.prismaService.client.activity.groupBy; +} diff --git a/server/src/core/comment/comment.module.ts b/server/src/core/comment/comment.module.ts index 8db99c7e7..9b23cebc6 100644 --- a/server/src/core/comment/comment.module.ts +++ b/server/src/core/comment/comment.module.ts @@ -1,19 +1,10 @@ import { Module } from '@nestjs/common'; -import { CommentService } from './services/comment.service'; -import { CommentResolver } from './resolvers/comment.resolver'; -import { CommentThreadTargetService } from './services/comment-thread-target.service'; -import { CommentThreadResolver } from './resolvers/comment-thread.resolver'; -import { CommentThreadService } from './services/comment-thread.service'; +import { CommentService } from './comment.service'; +import { CommentResolver } from './comment.resolver'; @Module({ - providers: [ - CommentService, - CommentThreadService, - CommentThreadTargetService, - CommentResolver, - CommentThreadResolver, - ], - exports: [CommentService, CommentThreadService, CommentThreadTargetService], + providers: [CommentService, CommentResolver], + exports: [CommentService], }) export class CommentModule {} diff --git a/server/src/core/comment/resolvers/comment.resolver.spec.ts b/server/src/core/comment/comment.resolver.spec.ts similarity index 90% rename from server/src/core/comment/resolvers/comment.resolver.spec.ts rename to server/src/core/comment/comment.resolver.spec.ts index 479bc5bec..ccc45ffab 100644 --- a/server/src/core/comment/resolvers/comment.resolver.spec.ts +++ b/server/src/core/comment/comment.resolver.spec.ts @@ -1,6 +1,6 @@ import { Test, TestingModule } from '@nestjs/testing'; -import { CommentService } from 'src/core/comment/services/comment.service'; +import { CommentService } from 'src/core/comment/comment.service'; import { AbilityFactory } from 'src/ability/ability.factory'; import { CommentResolver } from './comment.resolver'; diff --git a/server/src/core/comment/resolvers/comment.resolver.ts b/server/src/core/comment/comment.resolver.ts similarity index 95% rename from server/src/core/comment/resolvers/comment.resolver.ts rename to server/src/core/comment/comment.resolver.ts index 12ec2ac31..053ee74e1 100644 --- a/server/src/core/comment/resolvers/comment.resolver.ts +++ b/server/src/core/comment/comment.resolver.ts @@ -8,7 +8,7 @@ import { Workspace } from 'src/core/@generated/workspace/workspace.model'; import { AuthWorkspace } from 'src/decorators/auth-workspace.decorator'; import { CreateOneCommentArgs } from 'src/core/@generated/comment/create-one-comment.args'; import { Comment } from 'src/core/@generated/comment/comment.model'; -import { CommentService } from 'src/core/comment/services/comment.service'; +import { CommentService } from 'src/core/comment/comment.service'; import { PrismaSelector, PrismaSelect, diff --git a/server/src/core/comment/services/comment.service.spec.ts b/server/src/core/comment/comment.service.spec.ts similarity index 100% rename from server/src/core/comment/services/comment.service.spec.ts rename to server/src/core/comment/comment.service.spec.ts diff --git a/server/src/core/comment/services/comment.service.ts b/server/src/core/comment/comment.service.ts similarity index 100% rename from server/src/core/comment/services/comment.service.ts rename to server/src/core/comment/comment.service.ts diff --git a/server/src/core/comment/resolvers/comment-thread.resolver.ts b/server/src/core/comment/resolvers/comment-thread.resolver.ts deleted file mode 100644 index 362de7a3d..000000000 --- a/server/src/core/comment/resolvers/comment-thread.resolver.ts +++ /dev/null @@ -1,150 +0,0 @@ -import { Resolver, Args, Mutation, Query } from '@nestjs/graphql'; -import { UseGuards } from '@nestjs/common'; - -import { accessibleBy } from '@casl/prisma'; -import { Prisma } from '@prisma/client'; - -import { JwtAuthGuard } from 'src/guards/jwt.auth.guard'; -import { Workspace } from 'src/core/@generated/workspace/workspace.model'; -import { AuthWorkspace } from 'src/decorators/auth-workspace.decorator'; -import { CommentThread } from 'src/core/@generated/comment-thread/comment-thread.model'; -import { CreateOneCommentThreadArgs } from 'src/core/@generated/comment-thread/create-one-comment-thread.args'; -import { FindManyCommentThreadArgs } from 'src/core/@generated/comment-thread/find-many-comment-thread.args'; -import { CommentThreadService } from 'src/core/comment/services/comment-thread.service'; -import { UpdateOneCommentThreadArgs } from 'src/core/@generated/comment-thread/update-one-comment-thread.args'; -import { - PrismaSelector, - PrismaSelect, -} from 'src/decorators/prisma-select.decorator'; -import { AbilityGuard } from 'src/guards/ability.guard'; -import { CheckAbilities } from 'src/decorators/check-abilities.decorator'; -import { - CreateCommentThreadAbilityHandler, - DeleteCommentThreadAbilityHandler, - ReadCommentThreadAbilityHandler, - UpdateCommentThreadAbilityHandler, -} from 'src/ability/handlers/comment-thread.ability-handler'; -import { UserAbility } from 'src/decorators/user-ability.decorator'; -import { AppAbility } from 'src/ability/ability.factory'; -import { AffectedRows } from 'src/core/@generated/prisma/affected-rows.output'; -import { DeleteManyCommentThreadArgs } from 'src/core/@generated/comment-thread/delete-many-comment-thread.args'; - -@UseGuards(JwtAuthGuard) -@Resolver(() => CommentThread) -export class CommentThreadResolver { - constructor(private readonly commentThreadService: CommentThreadService) {} - - @Mutation(() => CommentThread, { - nullable: false, - }) - @UseGuards(AbilityGuard) - @CheckAbilities(CreateCommentThreadAbilityHandler) - async createOneCommentThread( - @Args() args: CreateOneCommentThreadArgs, - @AuthWorkspace() workspace: Workspace, - @PrismaSelector({ modelName: 'CommentThread' }) - prismaSelect: PrismaSelect<'CommentThread'>, - ): Promise> { - const createdCommentThread = await this.commentThreadService.create({ - data: { - ...args.data, - ...{ workspace: { connect: { id: workspace.id } } }, - commentThreadTargets: args.data?.commentThreadTargets?.createMany - ? { - createMany: { - data: args.data.commentThreadTargets.createMany.data.map( - (target) => ({ ...target, workspaceId: workspace.id }), - ), - }, - } - : undefined, - }, - select: prismaSelect.value, - } as Prisma.CommentThreadCreateArgs); - - return createdCommentThread; - } - - @Mutation(() => CommentThread, { - nullable: false, - }) - @UseGuards(AbilityGuard) - @CheckAbilities(UpdateCommentThreadAbilityHandler) - async updateOneCommentThread( - @Args() args: UpdateOneCommentThreadArgs, - @AuthWorkspace() workspace: Workspace, - @PrismaSelector({ modelName: 'CommentThread' }) - prismaSelect: PrismaSelect<'CommentThread'>, - ): Promise> { - // TODO: Do a proper check with recursion testing on args in a more generic place - for (const key in args.data) { - if (args.data[key]) { - for (const subKey in args.data[key]) { - if (JSON.stringify(args.data[key][subKey]) === '{}') { - delete args.data[key][subKey]; - } - } - } - - if (JSON.stringify(args.data[key]) === '{}') { - delete args.data[key]; - } - } - const updatedCommentThread = await this.commentThreadService.update({ - where: args.where, - data: { - ...args.data, - commentThreadTargets: args.data?.commentThreadTargets?.createMany - ? { - createMany: { - data: args.data.commentThreadTargets.createMany.data.map( - (target) => ({ ...target, workspaceId: workspace.id }), - ), - }, - } - : undefined, - }, - select: prismaSelect.value, - } as Prisma.CommentThreadUpdateArgs); - - return updatedCommentThread; - } - - @Query(() => [CommentThread]) - @UseGuards(AbilityGuard) - @CheckAbilities(ReadCommentThreadAbilityHandler) - async findManyCommentThreads( - @Args() args: FindManyCommentThreadArgs, - @UserAbility() ability: AppAbility, - @PrismaSelector({ modelName: 'CommentThread' }) - prismaSelect: PrismaSelect<'CommentThread'>, - ): Promise[]> { - const result = await this.commentThreadService.findMany({ - where: { - ...args.where, - AND: [accessibleBy(ability).CommentThread], - }, - orderBy: args.orderBy, - cursor: args.cursor, - take: args.take, - skip: args.skip, - distinct: args.distinct, - select: prismaSelect.value, - }); - - return result; - } - - @Mutation(() => AffectedRows, { - nullable: false, - }) - @UseGuards(AbilityGuard) - @CheckAbilities(DeleteCommentThreadAbilityHandler) - async deleteManyCommentThreads( - @Args() args: DeleteManyCommentThreadArgs, - ): Promise { - return this.commentThreadService.deleteMany({ - where: args.where, - }); - } -} diff --git a/server/src/core/comment/services/comment-thread-target.service.ts b/server/src/core/comment/services/comment-thread-target.service.ts deleted file mode 100644 index 508c35a45..000000000 --- a/server/src/core/comment/services/comment-thread-target.service.ts +++ /dev/null @@ -1,41 +0,0 @@ -import { Injectable } from '@nestjs/common'; - -import { PrismaService } from 'src/database/prisma.service'; - -@Injectable() -export class CommentThreadTargetService { - constructor(private readonly prismaService: PrismaService) {} - - // Find - findFirst = this.prismaService.client.commentThreadTarget.findFirst; - findFirstOrThrow = - this.prismaService.client.commentThreadTarget.findFirstOrThrow; - - findUnique = this.prismaService.client.commentThreadTarget.findUnique; - findUniqueOrThrow = - this.prismaService.client.commentThreadTarget.findUniqueOrThrow; - - findMany = this.prismaService.client.commentThreadTarget.findMany; - - // Create - create = this.prismaService.client.commentThreadTarget.create; - createMany = this.prismaService.client.commentThreadTarget.createMany; - - // Update - update = this.prismaService.client.commentThreadTarget.update; - upsert = this.prismaService.client.commentThreadTarget.upsert; - updateMany = this.prismaService.client.commentThreadTarget.updateMany; - - // Delete - delete = this.prismaService.client.commentThreadTarget.delete; - deleteMany = this.prismaService.client.commentThreadTarget.deleteMany; - - // Aggregate - aggregate = this.prismaService.client.commentThreadTarget.aggregate; - - // Count - count = this.prismaService.client.commentThreadTarget.count; - - // GroupBy - groupBy = this.prismaService.client.commentThreadTarget.groupBy; -} diff --git a/server/src/core/comment/services/comment-thread.service.ts b/server/src/core/comment/services/comment-thread.service.ts deleted file mode 100644 index 0f447c9fa..000000000 --- a/server/src/core/comment/services/comment-thread.service.ts +++ /dev/null @@ -1,39 +0,0 @@ -import { Injectable } from '@nestjs/common'; - -import { PrismaService } from 'src/database/prisma.service'; - -@Injectable() -export class CommentThreadService { - constructor(private readonly prismaService: PrismaService) {} - - // Find - findFirst = this.prismaService.client.commentThread.findFirst; - findFirstOrThrow = this.prismaService.client.commentThread.findFirstOrThrow; - - findUnique = this.prismaService.client.commentThread.findUnique; - findUniqueOrThrow = this.prismaService.client.commentThread.findUniqueOrThrow; - - findMany = this.prismaService.client.commentThread.findMany; - - // Create - create = this.prismaService.client.commentThread.create; - createMany = this.prismaService.client.commentThread.createMany; - - // Update - update = this.prismaService.client.commentThread.update; - upsert = this.prismaService.client.commentThread.upsert; - updateMany = this.prismaService.client.commentThread.updateMany; - - // Delete - delete = this.prismaService.client.commentThread.delete; - deleteMany = this.prismaService.client.commentThread.deleteMany; - - // Aggregate - aggregate = this.prismaService.client.commentThread.aggregate; - - // Count - count = this.prismaService.client.commentThread.count; - - // GroupBy - groupBy = this.prismaService.client.commentThread.groupBy; -} diff --git a/server/src/core/company/company-relations.resolver.spec.ts b/server/src/core/company/company-relations.resolver.spec.ts index b222a28fd..7cb12bbda 100644 --- a/server/src/core/company/company-relations.resolver.spec.ts +++ b/server/src/core/company/company-relations.resolver.spec.ts @@ -1,7 +1,7 @@ import { Test, TestingModule } from '@nestjs/testing'; -import { CommentThreadService } from 'src/core/comment/services/comment-thread.service'; -import { CommentService } from 'src/core/comment/services/comment.service'; +import { CommentService } from 'src/core/comment/comment.service'; +import { ActivityService } from 'src/core/activity/services/activity.service'; import { CompanyRelationsResolver } from './company-relations.resolver'; import { CompanyService } from './company.service'; @@ -18,7 +18,7 @@ describe('CompanyRelationsResolver', () => { useValue: {}, }, { - provide: CommentThreadService, + provide: ActivityService, useValue: {}, }, { diff --git a/server/src/core/company/company-relations.resolver.ts b/server/src/core/company/company-relations.resolver.ts index 2c2932b8b..f238c1b34 100644 --- a/server/src/core/company/company-relations.resolver.ts +++ b/server/src/core/company/company-relations.resolver.ts @@ -1,36 +1,36 @@ import { Resolver, ResolveField, Root, Int } from '@nestjs/graphql'; -import { CommentThread } from 'src/core/@generated/comment-thread/comment-thread.model'; import { Comment } from 'src/core/@generated/comment/comment.model'; import { Company } from 'src/core/@generated/company/company.model'; -import { CommentThreadService } from 'src/core/comment/services/comment-thread.service'; -import { CommentService } from 'src/core/comment/services/comment.service'; +import { CommentService } from 'src/core/comment/comment.service'; import { PrismaSelect, PrismaSelector, } from 'src/decorators/prisma-select.decorator'; +import { ActivityService } from 'src/core/activity/services/activity.service'; +import { Activity } from 'src/core/@generated/activity/activity.model'; @Resolver(() => Company) export class CompanyRelationsResolver { constructor( - private readonly commentThreadService: CommentThreadService, + private readonly activityService: ActivityService, private readonly commentService: CommentService, ) {} - @ResolveField(() => [CommentThread], { + @ResolveField(() => [Activity], { nullable: false, }) - async commentThreads( + async activities( @Root() company: Company, - @PrismaSelector({ modelName: 'CommentThread' }) - prismaSelect: PrismaSelect<'CommentThread'>, - ): Promise[]> { - return this.commentThreadService.findMany({ + @PrismaSelector({ modelName: 'Activity' }) + prismaSelect: PrismaSelect<'Activity'>, + ): Promise[]> { + return this.activityService.findMany({ where: { - commentThreadTargets: { + activityTargets: { some: { - commentableId: company.id, commentableType: 'Company', + commentableId: company.id, }, }, }, @@ -48,11 +48,11 @@ export class CompanyRelationsResolver { ): Promise[]> { return this.commentService.findMany({ where: { - commentThread: { - commentThreadTargets: { + activity: { + activityTargets: { some: { - commentableId: company.id, commentableType: 'Company', + commentableId: company.id, }, }, }, @@ -64,13 +64,13 @@ export class CompanyRelationsResolver { @ResolveField(() => Int, { nullable: false, }) - async _commentThreadCount(@Root() company: Company): Promise { - return this.commentThreadService.count({ + async _activityCount(@Root() company: Company): Promise { + return this.activityService.count({ where: { - commentThreadTargets: { + activityTargets: { some: { - commentableId: company.id, commentableType: 'Company', + commentableId: company.id, }, }, }, diff --git a/server/src/core/company/company.module.ts b/server/src/core/company/company.module.ts index e8f7e3e09..95c498547 100644 --- a/server/src/core/company/company.module.ts +++ b/server/src/core/company/company.module.ts @@ -1,13 +1,14 @@ import { Module } from '@nestjs/common'; import { CommentModule } from 'src/core/comment/comment.module'; +import { ActivityModule } from 'src/core/activity/activity.module'; import { CompanyService } from './company.service'; import { CompanyResolver } from './company.resolver'; import { CompanyRelationsResolver } from './company-relations.resolver'; @Module({ - imports: [CommentModule], + imports: [CommentModule, ActivityModule], providers: [CompanyService, CompanyResolver, CompanyRelationsResolver], exports: [CompanyService], }) diff --git a/server/src/core/core.module.ts b/server/src/core/core.module.ts index 4832e4409..63636a3a9 100644 --- a/server/src/core/core.module.ts +++ b/server/src/core/core.module.ts @@ -11,6 +11,7 @@ import { AnalyticsModule } from './analytics/analytics.module'; import { FileModule } from './file/file.module'; import { ClientConfigModule } from './client-config/client-config.module'; import { AttachmentModule } from './attachment/attachment.module'; +import { ActivityModule } from './activity/activity.module'; import { ViewModule } from './view/view.module'; @Module({ @@ -26,6 +27,7 @@ import { ViewModule } from './view/view.module'; FileModule, ClientConfigModule, AttachmentModule, + ActivityModule, ViewModule, ], exports: [ diff --git a/server/src/core/person/person-relations.resolver.spec.ts b/server/src/core/person/person-relations.resolver.spec.ts index 5f7cd6dc0..683c7d841 100644 --- a/server/src/core/person/person-relations.resolver.spec.ts +++ b/server/src/core/person/person-relations.resolver.spec.ts @@ -1,7 +1,7 @@ import { Test, TestingModule } from '@nestjs/testing'; -import { CommentThreadService } from 'src/core/comment/services/comment-thread.service'; -import { CommentService } from 'src/core/comment/services/comment.service'; +import { CommentService } from 'src/core/comment/comment.service'; +import { ActivityService } from 'src/core/activity/services/activity.service'; import { PersonRelationsResolver } from './person-relations.resolver'; import { PersonService } from './person.service'; @@ -18,7 +18,7 @@ describe('PersonRelationsResolver', () => { useValue: {}, }, { - provide: CommentThreadService, + provide: ActivityService, useValue: {}, }, { diff --git a/server/src/core/person/person-relations.resolver.ts b/server/src/core/person/person-relations.resolver.ts index 275aeaa30..eeb34f5e3 100644 --- a/server/src/core/person/person-relations.resolver.ts +++ b/server/src/core/person/person-relations.resolver.ts @@ -1,36 +1,36 @@ import { Resolver, Root, ResolveField, Int } from '@nestjs/graphql'; -import { CommentThread } from 'src/core/@generated/comment-thread/comment-thread.model'; import { Comment } from 'src/core/@generated/comment/comment.model'; import { Person } from 'src/core/@generated/person/person.model'; -import { CommentThreadService } from 'src/core/comment/services/comment-thread.service'; -import { CommentService } from 'src/core/comment/services/comment.service'; +import { CommentService } from 'src/core/comment/comment.service'; import { PrismaSelect, PrismaSelector, } from 'src/decorators/prisma-select.decorator'; +import { Activity } from 'src/core/@generated/activity/activity.model'; +import { ActivityService } from 'src/core/activity/services/activity.service'; @Resolver(() => Person) export class PersonRelationsResolver { constructor( - private readonly commentThreadService: CommentThreadService, + private readonly activityService: ActivityService, private readonly commentService: CommentService, ) {} - @ResolveField(() => [CommentThread], { + @ResolveField(() => [Activity], { nullable: false, }) - async commentThreads( + async activities( @Root() person: Person, - @PrismaSelector({ modelName: 'CommentThread' }) - prismaSelect: PrismaSelect<'CommentThread'>, - ): Promise[]> { - return await this.commentThreadService.findMany({ + @PrismaSelector({ modelName: 'Activity' }) + prismaSelect: PrismaSelect<'Activity'>, + ): Promise[]> { + return await this.activityService.findMany({ where: { - commentThreadTargets: { + activityTargets: { some: { - commentableId: person.id, commentableType: 'Person', + commentableId: person.id, }, }, }, @@ -48,11 +48,11 @@ export class PersonRelationsResolver { ): Promise[]> { return this.commentService.findMany({ where: { - commentThread: { - commentThreadTargets: { + activity: { + activityTargets: { some: { - commentableId: person.id, commentableType: 'Person', + commentableId: person.id, }, }, }, @@ -64,13 +64,13 @@ export class PersonRelationsResolver { @ResolveField(() => Int, { nullable: false, }) - async _commentThreadCount(@Root() person: Person): Promise { - return this.commentThreadService.count({ + async _activityCount(@Root() person: Person): Promise { + return this.activityService.count({ where: { - commentThreadTargets: { + activityTargets: { some: { - commentableId: person.id, commentableType: 'Person', + commentableId: person.id, }, }, }, diff --git a/server/src/core/person/person.module.ts b/server/src/core/person/person.module.ts index d57c0c1e4..9ca83ef93 100644 --- a/server/src/core/person/person.module.ts +++ b/server/src/core/person/person.module.ts @@ -1,13 +1,14 @@ import { Module } from '@nestjs/common'; import { CommentModule } from 'src/core/comment/comment.module'; +import { ActivityModule } from 'src/core/activity/activity.module'; import { PersonService } from './person.service'; import { PersonResolver } from './person.resolver'; import { PersonRelationsResolver } from './person-relations.resolver'; @Module({ - imports: [CommentModule, CommentModule], + imports: [CommentModule, ActivityModule], providers: [PersonService, PersonResolver, PersonRelationsResolver], exports: [PersonService], }) diff --git a/server/src/core/person/person.resolver.ts b/server/src/core/person/person.resolver.ts index 2b94fb81e..64281f4e0 100644 --- a/server/src/core/person/person.resolver.ts +++ b/server/src/core/person/person.resolver.ts @@ -18,7 +18,6 @@ import { UpdateOnePersonArgs } from 'src/core/@generated/person/update-one-perso import { CreateOnePersonArgs } from 'src/core/@generated/person/create-one-person.args'; import { AffectedRows } from 'src/core/@generated/prisma/affected-rows.output'; import { DeleteManyPersonArgs } from 'src/core/@generated/person/delete-many-person.args'; -import { Workspace } from 'src/core/@generated/workspace/workspace.model'; import { AuthWorkspace } from 'src/decorators/auth-workspace.decorator'; import { PrismaSelect, @@ -34,6 +33,7 @@ import { } from 'src/ability/handlers/person.ability-handler'; import { UserAbility } from 'src/decorators/user-ability.decorator'; import { AppAbility } from 'src/ability/ability.factory'; +import { Workspace } from 'src/core/@generated/workspace/workspace.model'; import { PersonService } from './person.service'; diff --git a/server/src/core/workspace/services/workspace.service.ts b/server/src/core/workspace/services/workspace.service.ts index b44afabb8..fb238db5b 100644 --- a/server/src/core/workspace/services/workspace.service.ts +++ b/server/src/core/workspace/services/workspace.service.ts @@ -109,11 +109,11 @@ export class WorkspaceService { refreshToken, attachment, comment, - commentThreadTarget, - commentThread, + activityTarget, + activity, } = this.prismaService.client; - const commentThreads = await commentThread.findMany({ + const activitys = await activity.findMany({ where: { authorId: userId }, }); @@ -142,12 +142,12 @@ export class WorkspaceService { comment.deleteMany({ where, }), - ...commentThreads.map(({ id: commentThreadId }) => - commentThreadTarget.deleteMany({ - where: { commentThreadId }, + ...activitys.map(({ id: activityId }) => + activityTarget.deleteMany({ + where: { activityId }, }), ), - commentThread.deleteMany({ + activity.deleteMany({ where, }), refreshToken.deleteMany({ diff --git a/server/src/database/migrations/20230724115133_rename_table_comment_thread_into_activity/migration.sql b/server/src/database/migrations/20230724115133_rename_table_comment_thread_into_activity/migration.sql index d55cf14d7..ef4086fa1 100644 --- a/server/src/database/migrations/20230724115133_rename_table_comment_thread_into_activity/migration.sql +++ b/server/src/database/migrations/20230724115133_rename_table_comment_thread_into_activity/migration.sql @@ -1,4 +1,3 @@ --- Create the new tables first, without any foreign key constraints -- Activities Table CREATE TABLE "activities" ( "id" TEXT NOT NULL, diff --git a/server/src/database/migrations/20230728061715_complete_comment_thread_migration/migration.sql b/server/src/database/migrations/20230728061715_complete_comment_thread_migration/migration.sql new file mode 100644 index 000000000..f5a52f80e --- /dev/null +++ b/server/src/database/migrations/20230728061715_complete_comment_thread_migration/migration.sql @@ -0,0 +1,69 @@ +/* + Warnings: + + - You are about to drop the `comment_thread_targets` table. If the table is not empty, all the data it contains will be lost. + - You are about to drop the `comment_threads` table. If the table is not empty, all the data it contains will be lost. + +*/ +-- DropForeignKey +ALTER TABLE "attachments" DROP CONSTRAINT "attachments_activityId_fkey"; + +-- DropForeignKey +ALTER TABLE "comment_thread_targets" DROP CONSTRAINT "comment_thread_targets_commentThreadId_fkey"; + +-- DropForeignKey +ALTER TABLE "comment_thread_targets" DROP CONSTRAINT "comment_thread_targets_workspaceId_fkey"; + +-- DropForeignKey +ALTER TABLE "comment_threads" DROP CONSTRAINT "comment_threads_assigneeId_fkey"; + +-- DropForeignKey +ALTER TABLE "comment_threads" DROP CONSTRAINT "comment_threads_authorId_fkey"; + +-- DropForeignKey +ALTER TABLE "comment_threads" DROP CONSTRAINT "comment_threads_workspaceId_fkey"; + +-- DropForeignKey +ALTER TABLE "comments" DROP CONSTRAINT "comments_commentThreadId_fkey"; + +-- AlterTable +ALTER TABLE "activity_targets" ADD COLUMN "commentableId" TEXT, +ADD COLUMN "commentableType" "CommentableType", +ALTER COLUMN "personId" DROP NOT NULL, +ALTER COLUMN "companyId" DROP NOT NULL; + +-- AlterTable +ALTER TABLE "comments" ADD COLUMN "activityId" TEXT; + +-- DropTable +DROP TABLE "comment_thread_targets"; + +-- DropTable +DROP TABLE "comment_threads"; + +-- AddForeignKey +ALTER TABLE "activities" ADD CONSTRAINT "activities_authorId_fkey" FOREIGN KEY ("authorId") REFERENCES "users"("id") ON DELETE RESTRICT ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "activities" ADD CONSTRAINT "activities_assigneeId_fkey" FOREIGN KEY ("assigneeId") REFERENCES "users"("id") ON DELETE SET NULL ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "activities" ADD CONSTRAINT "activities_workspaceId_fkey" FOREIGN KEY ("workspaceId") REFERENCES "workspaces"("id") ON DELETE RESTRICT ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "comments" ADD CONSTRAINT "comments_activityId_fkey" FOREIGN KEY ("activityId") REFERENCES "activities"("id") ON DELETE CASCADE ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "activity_targets" ADD CONSTRAINT "activity_targets_activityId_fkey" FOREIGN KEY ("activityId") REFERENCES "activities"("id") ON DELETE CASCADE ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "activity_targets" ADD CONSTRAINT "activity_targets_workspaceId_fkey" FOREIGN KEY ("workspaceId") REFERENCES "workspaces"("id") ON DELETE RESTRICT ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "activity_targets" ADD CONSTRAINT "activity_targets_personId_fkey" FOREIGN KEY ("personId") REFERENCES "people"("id") ON DELETE SET NULL ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "activity_targets" ADD CONSTRAINT "activity_targets_companyId_fkey" FOREIGN KEY ("companyId") REFERENCES "companies"("id") ON DELETE SET NULL ON UPDATE CASCADE; + +-- AddForeignKey +ALTER TABLE "attachments" ADD CONSTRAINT "attachments_activityId_fkey" FOREIGN KEY ("activityId") REFERENCES "activities"("id") ON DELETE RESTRICT ON UPDATE CASCADE; diff --git a/server/src/database/schema.prisma b/server/src/database/schema.prisma index a45e76d7d..8f2d37a0b 100644 --- a/server/src/database/schema.prisma +++ b/server/src/database/schema.prisma @@ -20,20 +20,20 @@ generator nestgraphql { fields_Validator_from = "class-validator" // All relations, only allow connect - decorate_all_type = "!(CommentThreadTarget*Input|UserSettingsUpdateOneRequiredWithoutUserNestedInput)" + decorate_all_type = "!(ActivityTarget*Input|UserSettingsUpdateOneRequiredWithoutUserNestedInput)" decorate_all_field = "*(create|connectOrCreate|update|upsert|delete|createMany|updateMany|deleteMany)" decorate_all_name = "HideField" decorate_all_from = "@nestjs/graphql" decorate_all_arguments = "[]" - // CommentThread: Only Allow targets createOrConnect / createMany - decorate_commentThreadTargets_type = "*CommentThreadTarget*Input" - decorate_commentThreadTargets_field = "*(update|upsert|updateMany)" - decorate_commentThreadTargets_name = "HideField" - decorate_commentThreadTargets_from = "@nestjs/graphql" - decorate_commentThreadTargets_arguments = "[]" + // Activity: Only Allow targets createOrConnect / createMany + decorate_activityTargets_type = "*ActivityTarget*Input" + decorate_activityTargets_field = "*(update|upsert|updateMany)" + decorate_activityTargets_name = "HideField" + decorate_activityTargets_from = "@nestjs/graphql" + decorate_activityTargets_arguments = "[]" - // CommentThread: Only Allow targets createOrConnect / createMany + // User Settings: Only Allow targets createOrConnect / createMany decorate_userSettings_type = "*UserSettingsUpdateOneRequiredWithoutUserNestedInput" decorate_userSettings_field = "!(update)" decorate_userSettings_name = "HideField" @@ -106,10 +106,10 @@ model User { refreshTokens RefreshToken[] comments Comment[] - authoredCommentThreads CommentThread[] @relation(name: "authoredCommentThreads") - assignedCommentThreads CommentThread[] @relation(name: "assignedCommentThreads") - settings UserSettings @relation(fields: [settingsId], references: [id]) - settingsId String @unique + authoredActivities Activity[] @relation(name: "authoredActivities") + assignedActivities Activity[] @relation(name: "assignedActivities") + settings UserSettings @relation(fields: [settingsId], references: [id]) + settingsId String @unique /// @TypeGraphQL.omit(input: true, output: true) deletedAt DateTime? @@ -164,20 +164,20 @@ model Workspace { workspaceMember WorkspaceMember[] companies Company[] people Person[] - commentThreads CommentThread[] + activities Activity[] comments Comment[] pipelines Pipeline[] pipelineStages PipelineStage[] pipelineProgresses PipelineProgress[] + activityTargets ActivityTarget[] viewFields ViewField[] /// @TypeGraphQL.omit(input: true, output: true) deletedAt DateTime? - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt - Attachment Attachment[] - CommentThreadTarget CommentThreadTarget[] + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + Attachment Attachment[] @@map("workspaces") } @@ -234,8 +234,9 @@ model Company { /// @TypeGraphQL.omit(input: true, output: true) deletedAt DateTime? - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + ActivityTarget ActivityTarget[] @@map("companies") } @@ -277,8 +278,9 @@ model Person { /// @TypeGraphQL.omit(input: true, output: true) deletedAt DateTime? - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt + createdAt DateTime @default(now()) + updatedAt DateTime @updatedAt + ActivityTarget ActivityTarget[] @@map("people") } @@ -311,30 +313,28 @@ enum ActivityType { Task } -model CommentThread { +model Activity { /// @Validator.IsString() /// @Validator.IsOptional() - id String @id @default(uuid()) - - commentThreadTargets CommentThreadTarget[] - comments Comment[] - /// @TypeGraphQL.omit(input: true, output: true) - workspace Workspace @relation(fields: [workspaceId], references: [id]) - /// @TypeGraphQL.omit(input: true, output: true) - workspaceId String - - authorId String - author User @relation(fields: [authorId], references: [id], name: "authoredCommentThreads") - - body String? - title String? - type ActivityType @default(Note) - + id String @id @default(uuid()) + body String? + title String? + type ActivityType @default(Note) reminderAt DateTime? dueAt DateTime? completedAt DateTime? - assignee User? @relation(fields: [assigneeId], references: [id], name: "assignedCommentThreads") - assigneeId String? + + activityTargets ActivityTarget[] + comments Comment[] + attachments Attachment[] + author User @relation(fields: [authorId], references: [id], name: "authoredActivities") + authorId String + assignee User? @relation(fields: [assigneeId], references: [id], name: "assignedActivities") + assigneeId String? + /// @TypeGraphQL.omit(input: true, output: true) + workspace Workspace @relation(fields: [workspaceId], references: [id]) + /// @TypeGraphQL.omit(input: true, output: true) + workspaceId String /// @TypeGraphQL.omit(input: true, output: true) deletedAt DateTime? @@ -342,9 +342,12 @@ model CommentThread { createdAt DateTime @default(now()) updatedAt DateTime @updatedAt - attachments Attachment[] + @@map("activities") +} - @@map("comment_threads") +enum CommentableType { + Person + Company } model Comment { @@ -354,12 +357,13 @@ model Comment { /// @Validator.IsString() body String - author User @relation(fields: [authorId], references: [id]) + author User @relation(fields: [authorId], references: [id]) authorId String - commentThread CommentThread @relation(fields: [commentThreadId], references: [id], onDelete: Cascade) + activity Activity? @relation(fields: [activityId], references: [id], onDelete: Cascade) + activityId String? commentThreadId String /// @TypeGraphQL.omit(input: true, output: true) - workspace Workspace @relation(fields: [workspaceId], references: [id]) + workspace Workspace @relation(fields: [workspaceId], references: [id]) /// @TypeGraphQL.omit(input: true, output: true) workspaceId String @@ -372,24 +376,25 @@ model Comment { @@map("comments") } -enum CommentableType { - Person - Company -} - -model CommentThreadTarget { +model ActivityTarget { /// @Validator.IsString() /// @Validator.IsOptional() id String @id @default(uuid()) - commentThread CommentThread @relation(fields: [commentThreadId], references: [id], onDelete: Cascade) - commentThreadId String - /// @TypeGraphQL.omit(input: true, output: false) - workspace Workspace? @relation(fields: [workspaceId], references: [id]) + activity Activity @relation(fields: [activityId], references: [id], onDelete: Cascade) + activityId String + commentableType CommentableType? + commentableId String? /// @TypeGraphQL.omit(input: true, output: true) - workspaceId String? - commentableType CommentableType - commentableId String + workspace Workspace @relation(fields: [workspaceId], references: [id]) + /// @TypeGraphQL.omit(input: true, output: true) + workspaceId String + + personId String? + person Person? @relation(fields: [personId], references: [id]) + + companyId String? + company Company? @relation(fields: [companyId], references: [id]) /// @TypeGraphQL.omit(input: true, output: true) deletedAt DateTime? @@ -397,7 +402,7 @@ model CommentThreadTarget { createdAt DateTime @default(now()) updatedAt DateTime @updatedAt - @@map("comment_thread_targets") + @@map("activity_targets") } model Pipeline { @@ -515,17 +520,16 @@ model Attachment { type AttachmentType name String - authorId String - author User @relation(fields: [authorId], references: [id], name: "authoredAttachments") - - activityId String - activity CommentThread @relation(fields: [activityId], references: [id]) - - /// @TypeGraphQL.omit(input: true, output: false) - workspace Workspace @relation(fields: [workspaceId], references: [id]) /// @TypeGraphQL.omit(input: true, output: true) workspaceId String + author User @relation(fields: [authorId], references: [id], name: "authoredAttachments") + authorId String + activity Activity @relation(fields: [activityId], references: [id]) + activityId String + + /// @TypeGraphQL.omit(input: true, output: false) + workspace Workspace @relation(fields: [workspaceId], references: [id]) /// @TypeGraphQL.omit(input: true, output: true) deletedAt DateTime? createdAt DateTime @default(now()) diff --git a/server/src/database/seeds/comments.ts b/server/src/database/seeds/comments.ts index acaf01034..18f779d6a 100644 --- a/server/src/database/seeds/comments.ts +++ b/server/src/database/seeds/comments.ts @@ -1,6 +1,6 @@ import { PrismaClient } from '@prisma/client'; export const seedComments = async (prisma: PrismaClient) => { - await prisma.commentThread.upsert({ + await prisma.activity.upsert({ where: { id: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb400' }, update: {}, create: { @@ -13,15 +13,15 @@ export const seedComments = async (prisma: PrismaClient) => { }, }); - await prisma.commentThreadTarget.upsert({ + await prisma.activityTarget.upsert({ where: { id: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb600' }, update: {}, create: { id: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb600', - workspaceId: 'twenty-7ed9d212-1c25-4d02-bf25-6aeccf7ea419', commentableType: 'Company', commentableId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfa408', - commentThreadId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb400', + activityId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb400', + workspaceId: 'twenty-7ed9d212-1c25-4d02-bf25-6aeccf7ea419', }, }); @@ -32,6 +32,7 @@ export const seedComments = async (prisma: PrismaClient) => { id: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb200', workspaceId: 'twenty-7ed9d212-1c25-4d02-bf25-6aeccf7ea419', body: 'Hi Félix ! How do you like your Twenty workspace?', + activityId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb400', commentThreadId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb400', authorId: 'twenty-ge256b39-3ec3-4fe3-8997-b76aa0bfa408', }, @@ -44,12 +45,13 @@ export const seedComments = async (prisma: PrismaClient) => { id: 'twenty-fe256b40-3ec3-4fe3-8997-b76aa0bfb200', workspaceId: 'twenty-7ed9d212-1c25-4d02-bf25-6aeccf7ea419', body: 'I love it!', + activityId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb400', commentThreadId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb400', authorId: 'twenty-gk256b39-3ec3-4fe3-8997-b76aa0bfa408', }, }); - await prisma.commentThread.upsert({ + await prisma.activity.upsert({ where: { id: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfc408' }, update: {}, create: { @@ -64,15 +66,15 @@ export const seedComments = async (prisma: PrismaClient) => { }, }); - await prisma.commentThreadTarget.upsert({ + await prisma.activityTarget.upsert({ where: { id: 'twenty-fe256b39-3ec3-4fe3-8997-a76aa0bfb600' }, update: {}, create: { id: 'twenty-fe256b39-3ec3-4fe3-8997-a76aa0bfb600', - workspaceId: 'twenty-7ed9d212-1c25-4d02-bf25-6aeccf7ea419', commentableType: 'Person', commentableId: 'twenty-755035db-623d-41fe-92e7-dd45b7c568e1', - commentThreadId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfc408', + activityId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfc408', + workspaceId: 'twenty-7ed9d212-1c25-4d02-bf25-6aeccf7ea419', }, }); @@ -83,12 +85,13 @@ export const seedComments = async (prisma: PrismaClient) => { id: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfb100', workspaceId: 'twenty-7ed9d212-1c25-4d02-bf25-6aeccf7ea419', body: 'I really like this comment thread feature!', + activityId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfc408', commentThreadId: 'twenty-fe256b39-3ec3-4fe3-8997-b76aa0bfc408', authorId: 'twenty-ge256b39-3ec3-4fe3-8997-b76aa0bfa408', }, }); - await prisma.commentThread.upsert({ + await prisma.activity.upsert({ where: { id: 'twenty-dev-fe256b39-3ec3-4fe3-8997-b76aaabfb408' }, update: {}, create: { @@ -100,15 +103,15 @@ export const seedComments = async (prisma: PrismaClient) => { }, }); - await prisma.commentThreadTarget.upsert({ + await prisma.activityTarget.upsert({ where: { id: 'twenty-dev-fe256b39-3ec3-4fe3-8997-a76aa0bfba00' }, update: {}, create: { id: 'twenty-dev-fe256b39-3ec3-4fe3-8997-a76aa0bfba00', - workspaceId: 'twenty-dev-7ed9d212-1c25-4d02-bf25-6aeccf7ea420', commentableType: 'Company', commentableId: 'twenty-dev-a674fa6c-1455-4c57-afaf-dd5dc086361e', - commentThreadId: 'twenty-dev-fe256b39-3ec3-4fe3-8997-b76aaabfb408', + activityId: 'twenty-dev-fe256b39-3ec3-4fe3-8997-b76aaabfb408', + workspaceId: 'twenty-dev-7ed9d212-1c25-4d02-bf25-6aeccf7ea420', }, }); @@ -119,6 +122,7 @@ export const seedComments = async (prisma: PrismaClient) => { id: 'twenty-dev-fe256b39-3ec3-4fe3-8997-b76aa0bfb000', workspaceId: 'twenty-dev-7ed9d212-1c25-4d02-bf25-6aeccf7ea420', body: 'I really like this comment thread feature!', + activityId: 'twenty-dev-fe256b39-3ec3-4fe3-8997-b76aaabfb408', commentThreadId: 'twenty-dev-fe256b39-3ec3-4fe3-8997-b76aaabfb408', authorId: 'twenty-dev-gk256b39-3ec3-4fe3-8997-b76aa0boa408', }, diff --git a/server/src/utils/prisma-select/model-select-map.ts b/server/src/utils/prisma-select/model-select-map.ts index bb286ef78..653508af3 100644 --- a/server/src/utils/prisma-select/model-select-map.ts +++ b/server/src/utils/prisma-select/model-select-map.ts @@ -9,9 +9,9 @@ export type ModelSelectMap = { Company: Prisma.CompanySelect; Person: Prisma.PersonSelect; RefreshToken: Prisma.RefreshTokenSelect; - CommentThread: Prisma.CommentThreadSelect; + Activity: Prisma.ActivitySelect; Comment: Prisma.CommentSelect; - CommentThreadTarget: Prisma.CommentThreadTargetSelect; + ActivityTarget: Prisma.ActivityTargetSelect; Pipeline: Prisma.PipelineSelect; PipelineStage: Prisma.PipelineStageSelect; PipelineProgress: Prisma.PipelineProgressSelect;