From f24e3e67430f755610babe9340cd899289b2f212 Mon Sep 17 00:00:00 2001 From: Denis Bykhov Date: Wed, 3 May 2023 13:32:23 +0600 Subject: [PATCH] Requests inbox (#3125) Signed-off-by: Denis Bykhov --- models/request/package.json | 2 + models/request/src/index.ts | 46 ++++++++++++++ models/request/src/plugin.ts | 8 ++- packages/theme/styles/_layouts.scss | 1 + plugins/contact-resources/src/utils.ts | 4 +- plugins/request-assets/lang/en.json | 6 +- plugins/request-assets/lang/ru.json | 6 +- .../src/components/EditRequest.svelte | 20 ++++++- .../components/NotificationRequestView.svelte | 49 +++++++++++++++ .../src/components/RequestActions.svelte | 26 +++++++- .../src/components/RequestLabel.svelte | 60 ++++++++++++------- .../src/components/RequestPresenter.svelte | 22 +------ .../components/RequestStatusPresenter.svelte | 19 +++--- .../activity/TxCreateRequest.svelte | 5 +- .../components/activity/TxRequestLabel.svelte | 5 +- plugins/request-resources/src/index.ts | 6 +- plugins/request-resources/src/plugin.ts | 4 +- plugins/request/src/index.ts | 4 +- .../src/components/Workbench.svelte | 31 +--------- server-plugins/request-resources/src/index.ts | 11 ++-- 20 files changed, 225 insertions(+), 110 deletions(-) create mode 100644 plugins/request-resources/src/components/NotificationRequestView.svelte diff --git a/models/request/package.json b/models/request/package.json index 987e5c8f45..11f9d971d0 100644 --- a/models/request/package.json +++ b/models/request/package.json @@ -34,6 +34,8 @@ "@hcengineering/model-view": "^0.6.0", "@hcengineering/model-chunter": "^0.6.0", "@hcengineering/request": "^0.6.0", + "@hcengineering/notification": "^0.6.10", + "@hcengineering/model-notification": "^0.6.0", "@hcengineering/activity": "^0.6.0", "@hcengineering/chunter": "^0.6.5", "@hcengineering/request-resources": "^0.6.0" diff --git a/models/request/src/index.ts b/models/request/src/index.ts index 006604ccbb..22effce900 100644 --- a/models/request/src/index.ts +++ b/models/request/src/index.ts @@ -37,6 +37,8 @@ import view from '@hcengineering/model-view' import { Request, RequestDecisionComment, RequestPresenter, RequestStatus } from '@hcengineering/request' import { AnyComponent } from '@hcengineering/ui' import request from './plugin' +import notification from '@hcengineering/notification' +import { generateClassNotificationTypes } from '@hcengineering/model-notification' export { requestId } from '@hcengineering/request' export { default } from './plugin' @@ -89,10 +91,54 @@ export function createModel (builder: Builder): void { presenter: request.component.RequestPresenter }) + builder.mixin(request.class.Request, core.class.Class, notification.mixin.NotificationObjectPresenter, { + presenter: request.component.NotificationRequestView + }) + builder.mixin(request.class.Request, core.class.Class, request.mixin.RequestPresenter, { presenter: request.component.RequestView }) + builder.mixin(request.class.Request, core.class.Class, notification.mixin.ClassCollaborators, { + fields: ['requested', 'createdBy'] + }) + + builder.createDoc( + notification.class.NotificationGroup, + core.space.Model, + { + label: request.string.Requests, + icon: request.icon.Requests, + objectClass: request.class.Request + }, + request.ids.RequestNotificationGroup + ) + + builder.createDoc( + notification.class.NotificationType, + core.space.Model, + { + hidden: false, + objectClass: request.class.Request, + txClasses: [core.class.TxCreateDoc], + generated: false, + group: request.ids.RequestNotificationGroup, + label: request.string.Requested, + providers: { + [notification.providers.PlatformNotification]: true + } + }, + request.ids.CreateRequestNotification + ) + + generateClassNotificationTypes( + builder, + request.class.Request, + request.ids.RequestNotificationGroup, + [], + ['comments', 'approved', 'rejected', 'status'] + ) + builder.createDoc( activity.class.TxViewlet, core.space.Model, diff --git a/models/request/src/plugin.ts b/models/request/src/plugin.ts index 88060367ec..b5063dcd87 100644 --- a/models/request/src/plugin.ts +++ b/models/request/src/plugin.ts @@ -20,6 +20,7 @@ import { requestId } from '@hcengineering/request' import request from '@hcengineering/request-resources/src/plugin' import { AnyComponent } from '@hcengineering/ui' import type { TxViewlet } from '@hcengineering/activity' +import type { NotificationGroup, NotificationType } from '@hcengineering/notification' export default mergeIds(requestId, request, { activity: { @@ -27,10 +28,13 @@ export default mergeIds(requestId, request, { RequestLabel: '' as AnyComponent }, component: { - EditRequest: '' as AnyComponent + EditRequest: '' as AnyComponent, + NotificationRequestView: '' as AnyComponent }, ids: { - TxRequestCreate: '' as Ref + TxRequestCreate: '' as Ref, + RequestNotificationGroup: '' as Ref, + CreateRequestNotification: '' as Ref }, string: { Status: '' as IntlString, diff --git a/packages/theme/styles/_layouts.scss b/packages/theme/styles/_layouts.scss index 8753df718b..806d2a45ac 100644 --- a/packages/theme/styles/_layouts.scss +++ b/packages/theme/styles/_layouts.scss @@ -747,6 +747,7 @@ a.no-line { .font-semi-bold { font-weight: 600; } .fs-bold { font-weight: 500; } .uppercase { text-transform: uppercase; } +.lower { text-transform: lowercase; } .text-left { text-align: left; } .over-underline { diff --git a/plugins/contact-resources/src/utils.ts b/plugins/contact-resources/src/utils.ts index 53badb257b..3cdf93f402 100644 --- a/plugins/contact-resources/src/utils.ts +++ b/plugins/contact-resources/src/utils.ts @@ -202,7 +202,9 @@ export async function resolveLocation (loc: Location): Promise - return await generateLocation(loc, id) + if (id !== undefined) { + return await generateLocation(loc, id) + } } async function generateLocation (loc: Location, id: Ref): Promise { diff --git a/plugins/request-assets/lang/en.json b/plugins/request-assets/lang/en.json index 4ee248978d..adc89bfc37 100644 --- a/plugins/request-assets/lang/en.json +++ b/plugins/request-assets/lang/en.json @@ -4,7 +4,7 @@ "Request": "Request", "Approve": "Approve", "Approved": "Approved", - "CreatedRequest": "Created a request", + "CreatedRequest": "Created a ", "For": "For", "Change": "Change", "Add": "Add", @@ -16,6 +16,8 @@ "Rejected": "Rejected", "Comment": "Comment", "PleaseTypeMessage": "Please type comment message to continue...", - "NoRequests": "No requests" + "NoRequests": "No requests", + "Cancel": "Cancel", + "Cancelled": "Cancelled" } } \ No newline at end of file diff --git a/plugins/request-assets/lang/ru.json b/plugins/request-assets/lang/ru.json index fad8f19f27..54be338f4d 100644 --- a/plugins/request-assets/lang/ru.json +++ b/plugins/request-assets/lang/ru.json @@ -4,7 +4,7 @@ "Request": "Запрос", "Approve": "Одобрить", "Approved": "Одобрено", - "CreatedRequest": "Создал запрос", + "CreatedRequest": "Создал(а)", "For": "Для", "Change": "Изменить", "Add": "Добавить", @@ -16,6 +16,8 @@ "Rejected": "Отклонен", "Comment": "Комментировать", "PleaseTypeMessage": "Пожалуйста оставьте коментарий чтобы продолжить...", - "NoRequests": "Нет запросов" + "NoRequests": "Нет запросов", + "Cancel": "Отменить", + "Cancelled": "Отменен" } } \ No newline at end of file diff --git a/plugins/request-resources/src/components/EditRequest.svelte b/plugins/request-resources/src/components/EditRequest.svelte index cc89703e0a..34f5482d82 100644 --- a/plugins/request-resources/src/components/EditRequest.svelte +++ b/plugins/request-resources/src/components/EditRequest.svelte @@ -15,12 +15,14 @@ {#if object !== undefined}
- + {#if doc} + + + + + + {/if}
diff --git a/plugins/request-resources/src/components/NotificationRequestView.svelte b/plugins/request-resources/src/components/NotificationRequestView.svelte new file mode 100644 index 0000000000..66565885d1 --- /dev/null +++ b/plugins/request-resources/src/components/NotificationRequestView.svelte @@ -0,0 +1,49 @@ + + + +
+ + + + {#if doc} + + + + {/if} +
+ + diff --git a/plugins/request-resources/src/components/RequestActions.svelte b/plugins/request-resources/src/components/RequestActions.svelte index 3deb714d45..2614363f34 100644 --- a/plugins/request-resources/src/components/RequestActions.svelte +++ b/plugins/request-resources/src/components/RequestActions.svelte @@ -21,6 +21,7 @@ import { getClient } from '@hcengineering/presentation' import { Request, RequestStatus } from '@hcengineering/request' import type { RefAction } from '@hcengineering/text-editor' + import { Button } from '@hcengineering/ui' import request from '../plugin' import Comments from './icons/Comments.svelte' import DocFail from './icons/DocFail.svelte' @@ -70,7 +71,18 @@ // We need to update backlinks before and after. await updateBacklinks(client, value.attachedTo, value.attachedToClass, value._id, message) - refInput.submit() + refInput.createAttachments() + loading = false + } + + async function comment (): Promise { + await client.addCollection(chunter.class.Comment, value.space, value._id, value._class, 'comments', { + message, + attachments + }) + + // We need to update backlinks before and after. + await updateBacklinks(client, value.attachedTo, value.attachedToClass, value._id, message) loading = false } @@ -99,9 +111,20 @@ } ] let loading = false + + async function cancel () { + await client.update(value, { + status: RequestStatus.Cancelled + }) + } {#if value.status === RequestStatus.Active} + {#if value.createdBy === me} +
+
+ {/if}
-
-
- {/if} - - + {/if} + + + {/if}
diff --git a/plugins/request-resources/src/components/RequestPresenter.svelte b/plugins/request-resources/src/components/RequestPresenter.svelte index db985c5d95..43187296a5 100644 --- a/plugins/request-resources/src/components/RequestPresenter.svelte +++ b/plugins/request-resources/src/components/RequestPresenter.svelte @@ -13,33 +13,13 @@ // limitations under the License. -->
- -
-
-
- {#if value.status === RequestStatus.Completed || value.status === RequestStatus.Rejected} - - {:else} - - {/if} -
- - {dte.getMonth() + 1}/{dte.getDay() + 1}-{(dte.getHours() * 60 + dte.getMinutes()).toString(7)} - -
-
-
diff --git a/plugins/request-resources/src/components/RequestStatusPresenter.svelte b/plugins/request-resources/src/components/RequestStatusPresenter.svelte index 0a7111aa15..2a0d3f66fc 100644 --- a/plugins/request-resources/src/components/RequestStatusPresenter.svelte +++ b/plugins/request-resources/src/components/RequestStatusPresenter.svelte @@ -16,22 +16,19 @@ import { IntlString } from '@hcengineering/platform' import { BooleanIcon, Label } from '@hcengineering/ui' import request from '../plugin' + import { RequestStatus } from '@hcengineering/request' - export let value: boolean + export let value: RequestStatus - function getBooleanLabel (value: boolean): IntlString { - if (value) return request.string.Completed - return request.string.Rejected + function getBooleanLabel (value: RequestStatus): IntlString { + if (value === RequestStatus.Completed) return request.string.Completed + if (value === RequestStatus.Rejected) return request.string.Rejected + return request.string.Cancelled } -
- +
+
diff --git a/plugins/request-resources/src/components/activity/TxCreateRequest.svelte b/plugins/request-resources/src/components/activity/TxCreateRequest.svelte index 4a11b74ae6..f57b3de2cc 100644 --- a/plugins/request-resources/src/components/activity/TxCreateRequest.svelte +++ b/plugins/request-resources/src/components/activity/TxCreateRequest.svelte @@ -17,6 +17,9 @@ import RequestPresenter from '../RequestPresenter.svelte' export let value: Request + export let isOwnTx: boolean - +{#if !isOwnTx} + +{/if} diff --git a/plugins/request-resources/src/components/activity/TxRequestLabel.svelte b/plugins/request-resources/src/components/activity/TxRequestLabel.svelte index 3fc0146b80..884cd32fd6 100644 --- a/plugins/request-resources/src/components/activity/TxRequestLabel.svelte +++ b/plugins/request-resources/src/components/activity/TxRequestLabel.svelte @@ -18,6 +18,7 @@ import RequestLabel from '../RequestLabel.svelte' export let value: Request + export let isOwnTx: boolean let request: Request | undefined = undefined const query = createQuery() @@ -25,7 +26,5 @@ {#if request} -
- -
+ {/if} diff --git a/plugins/request-resources/src/index.ts b/plugins/request-resources/src/index.ts index e38eacb2d3..32d8be5187 100644 --- a/plugins/request-resources/src/index.ts +++ b/plugins/request-resources/src/index.ts @@ -14,12 +14,12 @@ // import { Resources } from '@hcengineering/platform' -import RequestsPopup from './components/RequestsPopup.svelte' import TxCreateRequest from './components/activity/TxCreateRequest.svelte' import RequestLabel from './components/activity/TxRequestLabel.svelte' import EditRequest from './components/EditRequest.svelte' import RequestPresenter from './components/RequestPresenter.svelte' import RequestView from './components/RequestView.svelte' +import NotificationRequestView from './components/NotificationRequestView.svelte' export default async (): Promise => ({ activity: { @@ -27,9 +27,9 @@ export default async (): Promise => ({ TxCreateRequest }, component: { - RequestsPopup, EditRequest, RequestPresenter, - RequestView + RequestView, + NotificationRequestView } }) diff --git a/plugins/request-resources/src/plugin.ts b/plugins/request-resources/src/plugin.ts index 6e47003405..b773217666 100644 --- a/plugins/request-resources/src/plugin.ts +++ b/plugins/request-resources/src/plugin.ts @@ -22,6 +22,7 @@ export default mergeIds(requestId, request, { Approve: '' as IntlString, Approved: '' as IntlString, CreatedRequest: '' as IntlString, + Cancel: '' as IntlString, For: '' as IntlString, Change: '' as IntlString, Add: '' as IntlString, @@ -32,6 +33,7 @@ export default mergeIds(requestId, request, { Rejected: '' as IntlString, Comment: '' as IntlString, PleaseTypeMessage: '' as IntlString, - NoRequests: '' as IntlString + NoRequests: '' as IntlString, + Cancelled: '' as IntlString } }) diff --git a/plugins/request/src/index.ts b/plugins/request/src/index.ts index a833a6ecd1..5b05ad2b8a 100644 --- a/plugins/request/src/index.ts +++ b/plugins/request/src/index.ts @@ -44,7 +44,8 @@ export interface RequestDecisionComment extends Comment {} export enum RequestStatus { Active = 'Active', Completed = 'Completed', - Rejected = 'Rejected' + Rejected = 'Rejected', + Cancelled = 'Cancelled' } /** @@ -71,7 +72,6 @@ const request = plugin(requestId, { RequestPresenter: '' as Ref> }, component: { - RequestsPopup: '' as AnyComponent, RequestPresenter: '' as AnyComponent, RequestView: '' as AnyComponent }, diff --git a/plugins/workbench-resources/src/components/Workbench.svelte b/plugins/workbench-resources/src/components/Workbench.svelte index 36f1620443..35b0b7e61d 100644 --- a/plugins/workbench-resources/src/components/Workbench.svelte +++ b/plugins/workbench-resources/src/components/Workbench.svelte @@ -20,8 +20,7 @@ import notification, { notificationId } from '@hcengineering/notification' import { BrowserNotificatator, NotificationClientImpl } from '@hcengineering/notification-resources' import { IntlString, getMetadata, getResource } from '@hcengineering/platform' - import { createQuery, getClient, configurationStore } from '@hcengineering/presentation' - import request, { RequestStatus, requestId } from '@hcengineering/request' + import { configurationStore, createQuery, getClient } from '@hcengineering/presentation' import { AnyComponent, CompAndProps, @@ -60,11 +59,11 @@ import AccountPopup from './AccountPopup.svelte' import AppItem from './AppItem.svelte' import Applications from './Applications.svelte' + import Logo from './Logo.svelte' import NavHeader from './NavHeader.svelte' import Navigator from './Navigator.svelte' import SpaceView from './SpaceView.svelte' import Settings from './icons/Settings.svelte' - import Logo from './Logo.svelte' import TopMenu from './icons/TopMenu.svelte' let contentPanel: HTMLElement @@ -159,24 +158,6 @@ } ) - let hasRequests = false - const requestQuery = createQuery() - - $: $configurationStore.has(requestId) || - requestQuery.query( - request.class.Request, - { - requested: account._id, - status: RequestStatus.Active - }, - (res) => - (hasRequests = - res.filter( - (p) => - p.requested.filter((a) => a === account._id).length > p.approved.filter((a) => a === account._id).length - ).length > 0) - ) - onDestroy( location.subscribe(async (loc) => { closeTooltip() @@ -606,14 +587,6 @@ on:click={() => showPopup(calendar.component.RemindersPopup, {}, notifyPosition)} /> {/if} - {#if $configurationStore.has(requestId)} - showPopup(request.component.RequestsPopup, {}, notifyPosition)} - notify={hasRequests} - /> - {/if}