Mention notification (#991)

Signed-off-by: Denis Bykhov <80476319+BykhovDenis@users.noreply.github.com>
This commit is contained in:
Denis Bykhov
2022-02-11 10:18:55 +01:00
committed by GitHub
parent ef4d632047
commit 7867150051
66 changed files with 1079 additions and 198 deletions
+107 -15
View File
@@ -63,6 +63,7 @@ specifiers:
'@rush-temp/model-server-attachment': file:./projects/model-server-attachment.tgz
'@rush-temp/model-server-contact': file:./projects/model-server-contact.tgz
'@rush-temp/model-server-core': file:./projects/model-server-core.tgz
'@rush-temp/model-server-notification': file:./projects/model-server-notification.tgz
'@rush-temp/model-setting': file:./projects/model-setting.tgz
'@rush-temp/model-task': file:./projects/model-task.tgz
'@rush-temp/model-telegram': file:./projects/model-telegram.tgz
@@ -72,6 +73,7 @@ specifiers:
'@rush-temp/model-workbench': file:./projects/model-workbench.tgz
'@rush-temp/mongo': file:./projects/mongo.tgz
'@rush-temp/notification': file:./projects/notification.tgz
'@rush-temp/notification-assets': file:./projects/notification-assets.tgz
'@rush-temp/notification-resources': file:./projects/notification-resources.tgz
'@rush-temp/panel': file:./projects/panel.tgz
'@rush-temp/platform': file:./projects/platform.tgz
@@ -90,6 +92,8 @@ specifiers:
'@rush-temp/server-contact': file:./projects/server-contact.tgz
'@rush-temp/server-contact-resources': file:./projects/server-contact-resources.tgz
'@rush-temp/server-core': file:./projects/server-core.tgz
'@rush-temp/server-notification': file:./projects/server-notification.tgz
'@rush-temp/server-notification-resources': file:./projects/server-notification-resources.tgz
'@rush-temp/server-token': file:./projects/server-token.tgz
'@rush-temp/server-tool': file:./projects/server-tool.tgz
'@rush-temp/server-ws': file:./projects/server-ws.tgz
@@ -264,6 +268,7 @@ dependencies:
'@rush-temp/model-server-attachment': file:projects/model-server-attachment.tgz_typescript@4.5.4
'@rush-temp/model-server-contact': file:projects/model-server-contact.tgz_typescript@4.5.4
'@rush-temp/model-server-core': file:projects/model-server-core.tgz_typescript@4.5.4
'@rush-temp/model-server-notification': file:projects/model-server-notification.tgz_typescript@4.5.4
'@rush-temp/model-setting': file:projects/model-setting.tgz_typescript@4.5.4
'@rush-temp/model-task': file:projects/model-task.tgz_typescript@4.5.4
'@rush-temp/model-telegram': file:projects/model-telegram.tgz_typescript@4.5.4
@@ -273,6 +278,7 @@ dependencies:
'@rush-temp/model-workbench': file:projects/model-workbench.tgz_typescript@4.5.4
'@rush-temp/mongo': file:projects/mongo.tgz
'@rush-temp/notification': file:projects/notification.tgz
'@rush-temp/notification-assets': file:projects/notification-assets.tgz_typescript@4.5.4
'@rush-temp/notification-resources': file:projects/notification-resources.tgz_096c09b0b673a57c275d9767a12070b1
'@rush-temp/panel': file:projects/panel.tgz_096c09b0b673a57c275d9767a12070b1
'@rush-temp/platform': file:projects/platform.tgz
@@ -291,6 +297,8 @@ dependencies:
'@rush-temp/server-contact': file:projects/server-contact.tgz
'@rush-temp/server-contact-resources': file:projects/server-contact-resources.tgz
'@rush-temp/server-core': file:projects/server-core.tgz
'@rush-temp/server-notification': file:projects/server-notification.tgz
'@rush-temp/server-notification-resources': file:projects/server-notification-resources.tgz
'@rush-temp/server-token': file:projects/server-token.tgz
'@rush-temp/server-tool': file:projects/server-tool.tgz
'@rush-temp/server-ws': file:projects/server-ws.tgz
@@ -11187,7 +11195,7 @@ packages:
dev: false
file:projects/activity-resources.tgz_096c09b0b673a57c275d9767a12070b1:
resolution: {integrity: sha512-DTAIFUH5vy1h9mqxFrr25BYnjgndQ7HFIozOVU7lBlRHQJ2v9x1fWdKvLr9Srg+E7OeN2GawVcx19GUZ2eW/zg==, tarball: file:projects/activity-resources.tgz}
resolution: {integrity: sha512-o6RpdrtwnGmVtudJ14BdbkVOXYJ2kWdlC8BrM7HZnHNlWRbCoTUX9wAXdyOvwbkxcXbWANNNb8B9v9A+BE9f4Q==, tarball: file:projects/activity-resources.tgz}
id: file:projects/activity-resources.tgz
name: '@rush-temp/activity-resources'
version: 0.0.0
@@ -11377,7 +11385,7 @@ packages:
dev: false
file:projects/chunter.tgz:
resolution: {integrity: sha512-D/Ar+jZ9VwOidVBlO8Kh18DjmojP9ILhHojkN4NsoZ9t1ZoJ8/qiiq3TrEm81KHDqb1NyOm+Bcr8TlhkjchB2g==, tarball: file:projects/chunter.tgz}
resolution: {integrity: sha512-Yu9qSoDiPa7br3OD/0UGkdUX+Xb2woPmQWhyNpKvSwMDga++PcU2MWl8/6mASwFGKszAB7ybq/T4l/y7VMaKqg==, tarball: file:projects/chunter.tgz}
name: '@rush-temp/chunter'
version: 0.0.0
dependencies:
@@ -12048,7 +12056,7 @@ packages:
dev: false
file:projects/lead-resources.tgz_096c09b0b673a57c275d9767a12070b1:
resolution: {integrity: sha512-W842udh6/87OvajsjespWfSRZhSUJZPkGDSHCaMjtSePN5T4nL2EkNGR66mIi1RW88oAoyd3VPx8MSZmUWnCGQ==, tarball: file:projects/lead-resources.tgz}
resolution: {integrity: sha512-od6TTUKq72g4CBbHS06/M64kzZK//B9NF7aftYl91RVwL+gm5JQLFCLwksdo4NE7VSyb7VWop199pYfMaKOcdg==, tarball: file:projects/lead-resources.tgz}
id: file:projects/lead-resources.tgz
name: '@rush-temp/lead-resources'
version: 0.0.0
@@ -12201,7 +12209,7 @@ packages:
dev: false
file:projects/model-all.tgz_typescript@4.5.4:
resolution: {integrity: sha512-Q1uN1ojy8Xc1Q2hsrrBqQrwdhkJgfGu90yb/mtHmDDb+WCguVe1JlPL9jbLV0f39wY5qnCzByDApK2FHftgVlA==, tarball: file:projects/model-all.tgz}
resolution: {integrity: sha512-KDrsTCCCt8hoQSwtTAQOsgbNjHRb9g270jtlXlT320EbfHNUslOzMLwns850SHjoA+6XxerLV/ItBBPMc4xCUw==, tarball: file:projects/model-all.tgz}
id: file:projects/model-all.tgz
name: '@rush-temp/model-all'
version: 0.0.0
@@ -12394,7 +12402,7 @@ packages:
dev: false
file:projects/model-notification.tgz_typescript@4.5.4:
resolution: {integrity: sha512-q/JNneErW66xgCE5Yc/7bPkeUXwiEUJw95gbYt5uDTeuuzK0TrP77epbfSaWqkH7kP9SjqKrBwWPdm+M64q98g==, tarball: file:projects/model-notification.tgz}
resolution: {integrity: sha512-oXjmLAI4ablTqm5zdk23LYWTRRdqLGxshn164t87FLm4T/6sFK7xlikIuxGNn+XED0/m1T9ShPXEwXcYFJ/YQw==, tarball: file:projects/model-notification.tgz}
id: file:projects/model-notification.tgz
name: '@rush-temp/model-notification'
version: 0.0.0
@@ -12538,6 +12546,27 @@ packages:
- typescript
dev: false
file:projects/model-server-notification.tgz_typescript@4.5.4:
resolution: {integrity: sha512-bO0DgNGdJGxJjDU05x1HPNHfprIFhRYhauMT9eH4zKMlsQZNO5Rx5h77SxepW2HiAxVYMqjOR2GwsTN3h7C8wQ==, tarball: file:projects/model-server-notification.tgz}
id: file:projects/model-server-notification.tgz
name: '@rush-temp/model-server-notification'
version: 0.0.0
dependencies:
'@rushstack/heft': 0.41.8
'@types/heft-jest': 1.0.2
'@typescript-eslint/eslint-plugin': 5.7.0_c25e8c1f4f4f7aaed27aa6f9ce042237
'@typescript-eslint/parser': 5.7.0_eslint@7.32.0+typescript@4.5.4
eslint: 7.32.0
eslint-config-standard-with-typescript: 21.0.1_ce2fa0c4dfa1c256100cababd749a13a
eslint-plugin-import: 2.25.3_eslint@7.32.0
eslint-plugin-node: 11.1.0_eslint@7.32.0
eslint-plugin-promise: 5.2.0_eslint@7.32.0
prettier: 2.5.1
transitivePeerDependencies:
- supports-color
- typescript
dev: false
file:projects/model-setting.tgz_typescript@4.5.4:
resolution: {integrity: sha512-zwbVN3PDOfDeqGcL36IHQIufdePTd68yLUm83rfIg4v8+uilseid981y/BrAysmxTXAfhVYWlDmtYXvNPS4DMQ==, tarball: file:projects/model-setting.tgz}
id: file:projects/model-setting.tgz
@@ -12728,8 +12757,30 @@ packages:
- supports-color
dev: false
file:projects/notification-assets.tgz_typescript@4.5.4:
resolution: {integrity: sha512-2K6QTmVeQ8n4QRF37QQPTIGFDwzu9L9gWQU1hFrY0JURiX3wKoTX+tLYnqdr/i4QKQFG9DMYxrunrOvRu8kelQ==, tarball: file:projects/notification-assets.tgz}
id: file:projects/notification-assets.tgz
name: '@rush-temp/notification-assets'
version: 0.0.0
dependencies:
'@rushstack/heft': 0.41.8
'@types/heft-jest': 1.0.2
'@types/node': 16.11.14
'@typescript-eslint/eslint-plugin': 5.7.0_c25e8c1f4f4f7aaed27aa6f9ce042237
'@typescript-eslint/parser': 5.7.0_eslint@7.32.0+typescript@4.5.4
eslint: 7.32.0
eslint-config-standard-with-typescript: 21.0.1_ce2fa0c4dfa1c256100cababd749a13a
eslint-plugin-import: 2.25.3_eslint@7.32.0
eslint-plugin-node: 11.1.0_eslint@7.32.0
eslint-plugin-promise: 5.2.0_eslint@7.32.0
prettier: 2.5.1
transitivePeerDependencies:
- supports-color
- typescript
dev: false
file:projects/notification-resources.tgz_096c09b0b673a57c275d9767a12070b1:
resolution: {integrity: sha512-jOFuqeLEJ/3BNsAhz8NxibKKTkKtu1a8KqSO434S51HidRwdUBUY8lwZUB1UA97OFi/O7r3E4CGE0ERAdQWn0A==, tarball: file:projects/notification-resources.tgz}
resolution: {integrity: sha512-raqBx9exX10O9GZ0ltv6U0XgNO1DZxV5HzvCjACbdqL9C9wjlxcFci+0iOpwSLxMzPZn1IkkKDo18q5bH2oC7g==, tarball: file:projects/notification-resources.tgz}
id: file:projects/notification-resources.tgz
name: '@rush-temp/notification-resources'
version: 0.0.0
@@ -12766,7 +12817,7 @@ packages:
dev: false
file:projects/notification.tgz:
resolution: {integrity: sha512-VOGvKSMA5Utp3zuIYzvaHujYwS2ObDBtjrzKJzWDn8RtQo8zW8nOYjEOIDDIvXKGZlpl/5v62pDsEBiCQ/yNhw==, tarball: file:projects/notification.tgz}
resolution: {integrity: sha512-5pLpWTSQqSQ3UavtuHcWcLFP/gUyFTnP74LP+WsAmW5RhoYFxew/x7canzh6Oeq0DpaX7CxXUqmKtv8oCUvQkg==, tarball: file:projects/notification.tgz}
name: '@rush-temp/notification'
version: 0.0.0
dependencies:
@@ -12937,7 +12988,7 @@ packages:
dev: false
file:projects/prod.tgz_sass@1.45.0+typescript@4.5.4:
resolution: {integrity: sha512-DK9VDDqiYj34A7zgq+FHvonq4RGVr/Ozyjv7QR1HyNaUXnjYTM4lMV3sFjhXLeg2oCFY4J9nU2U1S4zTDoFEYA==, tarball: file:projects/prod.tgz}
resolution: {integrity: sha512-+ke/wA1+S6z6mgIO2IAwtov8K5Zpc4ScgRc+cdU34ie7/5JpPmdoQhDgxG3QbPrf+BlADvJEaVOVZRvml16TVw==, tarball: file:projects/prod.tgz}
id: file:projects/prod.tgz
name: '@rush-temp/prod'
version: 0.0.0
@@ -13029,7 +13080,7 @@ packages:
dev: false
file:projects/recruit-resources.tgz_096c09b0b673a57c275d9767a12070b1:
resolution: {integrity: sha512-NgcfcFmKVD0ojJbtjT3yvD//m1x3koZpBdkLryhSKtQMhzcuZD9GpBmVbRnPtLGBrDMSALasx1NB5JMxxDPLFQ==, tarball: file:projects/recruit-resources.tgz}
resolution: {integrity: sha512-8pFvHj9M1cjOrdU5vQPrYmV0Yqd76ErwcRrAuiiLXpKIpYqlRdAXTb9Xe34PygnwWRI3icjB+dl22AINYksbHA==, tarball: file:projects/recruit-resources.tgz}
id: file:projects/recruit-resources.tgz
name: '@rush-temp/recruit-resources'
version: 0.0.0
@@ -13218,6 +13269,47 @@ packages:
- supports-color
dev: false
file:projects/server-notification-resources.tgz:
resolution: {integrity: sha512-9EXWxHdVb5DvmZORxWPquKpxThiRV6zaEtpFbat4drf5i/br5cERKka5+oBJK27WyYYeB8rUGjjQ7AFx/dJzbQ==, tarball: file:projects/server-notification-resources.tgz}
name: '@rush-temp/server-notification-resources'
version: 0.0.0
dependencies:
'@rushstack/heft': 0.41.8
'@types/heft-jest': 1.0.2
'@typescript-eslint/eslint-plugin': 5.7.0_c25e8c1f4f4f7aaed27aa6f9ce042237
'@typescript-eslint/parser': 5.7.0_eslint@7.32.0+typescript@4.5.4
eslint: 7.32.0
eslint-config-standard-with-typescript: 21.0.1_ce2fa0c4dfa1c256100cababd749a13a
eslint-plugin-import: 2.25.3_eslint@7.32.0
eslint-plugin-node: 11.1.0_eslint@7.32.0
eslint-plugin-promise: 5.2.0_eslint@7.32.0
prettier: 2.5.1
typescript: 4.5.4
transitivePeerDependencies:
- supports-color
dev: false
file:projects/server-notification.tgz:
resolution: {integrity: sha512-gM+ROlR5RxqwvyRbfKGpZzsd/41J8Qx+kub8xjs5nKB9KyJRB0QoWtTKwaUBiI1S/JNMfi/3rAFZOWlbcV3sbQ==, tarball: file:projects/server-notification.tgz}
name: '@rush-temp/server-notification'
version: 0.0.0
dependencies:
'@rushstack/heft': 0.41.8
'@types/heft-jest': 1.0.2
'@types/node': 16.11.14
'@typescript-eslint/eslint-plugin': 5.7.0_c25e8c1f4f4f7aaed27aa6f9ce042237
'@typescript-eslint/parser': 5.7.0_eslint@7.32.0+typescript@4.5.4
eslint: 7.32.0
eslint-config-standard-with-typescript: 21.0.1_ce2fa0c4dfa1c256100cababd749a13a
eslint-plugin-import: 2.25.3_eslint@7.32.0
eslint-plugin-node: 11.1.0_eslint@7.32.0
eslint-plugin-promise: 5.2.0_eslint@7.32.0
prettier: 2.5.1
typescript: 4.5.4
transitivePeerDependencies:
- supports-color
dev: false
file:projects/server-token.tgz:
resolution: {integrity: sha512-74lvKW1J8vMQI7r+UUFCO8KDItftmBVTc9ecLL9kbWHdFT/kfR1ua57O8XG7MMJDmBVsWylHmM1kr6lxwNpNBA==, tarball: file:projects/server-token.tgz}
name: '@rush-temp/server-token'
@@ -13297,7 +13389,7 @@ packages:
dev: false
file:projects/server.tgz:
resolution: {integrity: sha512-b5qcL1erYSk29hFzWoJhG7GbtLdoTbEUHbScHKs7lLsQvftiiZmQRmuVcP8TVjiR3yTuMRJDt4ghH2d2UF9KIw==, tarball: file:projects/server.tgz}
resolution: {integrity: sha512-SuwXbo0xvalgyA3m9i/bbm9ae2I3Tx548KKj8wDffAJxDq0t0tqncuVtUmhrwG06HD9p5myf165I6apGZZocSg==, tarball: file:projects/server.tgz}
name: '@rush-temp/server'
version: 0.0.0
dependencies:
@@ -13349,7 +13441,7 @@ packages:
dev: false
file:projects/setting-resources.tgz_096c09b0b673a57c275d9767a12070b1:
resolution: {integrity: sha512-64E4dI7SY+8qkmtk5dn8wbbxOSOqM+AD4Xh+i0BTv09Fhafe/TAcYLdByY5jzVkLmBohrYgBioZJcPbmulsvXg==, tarball: file:projects/setting-resources.tgz}
resolution: {integrity: sha512-SwFlNFhQYEi0au+47ljHLl/kE1MKP2Oi290r8xZJL4VMNUHzTsKiHlS7teyE7p1IdGar1AIUm2Xi3JveR5NFIA==, tarball: file:projects/setting-resources.tgz}
id: file:projects/setting-resources.tgz
name: '@rush-temp/setting-resources'
version: 0.0.0
@@ -13579,7 +13671,7 @@ packages:
dev: false
file:projects/templates-resources.tgz_096c09b0b673a57c275d9767a12070b1:
resolution: {integrity: sha512-dsQP6LQ9+rxBOtUE2GXjmu7lhsQUAtP3ZWdzfo58ncdXao64Dn8w2nYrrUZ9dz7rcxwOPP3oHsrK7N2Egs1CMw==, tarball: file:projects/templates-resources.tgz}
resolution: {integrity: sha512-ms8wJBkOIYY64ptCGC6pQ6M+jQrKrVtJBLbDJNtp6Fxo+D1G8ksbg1S80hvpeZctOhUK14j3AkVt90IYgtgLbA==, tarball: file:projects/templates-resources.tgz}
id: file:projects/templates-resources.tgz
name: '@rush-temp/templates-resources'
version: 0.0.0
@@ -13614,7 +13706,7 @@ packages:
dev: false
file:projects/templates.tgz:
resolution: {integrity: sha512-GRoSidgyl5TL1m7EI6J/XuUCM7aQ8zp5jH8yl8oDXPHG2rS2v+7pSz9ccBE/ynC0pUkxKL1oSgDRMq9eAXC4Ag==, tarball: file:projects/templates.tgz}
resolution: {integrity: sha512-Ho7HWi1cbb5DLF8usV/ihT2hq6QZrwJapJOipSCnAdFLg9bdK+s3QqeeBuhsieJ0lur1rYMIwOW89g0UVsKwNg==, tarball: file:projects/templates.tgz}
name: '@rush-temp/templates'
version: 0.0.0
dependencies:
@@ -13739,7 +13831,7 @@ packages:
dev: false
file:projects/tool.tgz:
resolution: {integrity: sha512-tQSiv1J1yUul6SD2WNyzzSCJeS1VCZgWkun9xGIJELvQ+iZN6S4fznI35eMLBppJWD0XIYHmeOzNCfjX4PWw7g==, tarball: file:projects/tool.tgz}
resolution: {integrity: sha512-g3G79v0AQpHzqbZpmFsGU4wNu3BIcTMgR/Rod6Cfi9w0TpNS1XnSSckZeHB0LtTOovvFbj82x5ESBEwq1g0hFA==, tarball: file:projects/tool.tgz}
name: '@rush-temp/tool'
version: 0.0.0
dependencies:
@@ -13914,7 +14006,7 @@ packages:
dev: false
file:projects/workbench-resources.tgz_096c09b0b673a57c275d9767a12070b1:
resolution: {integrity: sha512-yWHOAPBVj1y9VbkYHOaANIkCbBfQOkKKvxj2dEFK3It4WUN/jxZSPqrmW1/ZNkENZVaWzRL1VY6uGhJJ5dwgFQ==, tarball: file:projects/workbench-resources.tgz}
resolution: {integrity: sha512-zqDa0vWNFseFg/iea/NI651RzhI018W2GA8H5dC3O2CXTkwTCUPGNK00HzqTTxWTYTNZ0tQ+5EI7+n4bs+n56w==, tarball: file:projects/workbench-resources.tgz}
id: file:projects/workbench-resources.tgz
name: '@rush-temp/workbench-resources'
version: 0.0.0
+3
View File
@@ -94,10 +94,13 @@
"@anticrm/server-attachment-resources": "~0.6.0",
"@anticrm/server-contact": "~0.6.1",
"@anticrm/server-contact-resources": "~0.6.0",
"@anticrm/server-notification": "~0.6.0",
"@anticrm/server-notification-resources": "~0.6.0",
"@anticrm/templates": "~0.6.0",
"@anticrm/templates-assets": "~0.6.0",
"@anticrm/templates-resources": "~0.6.0",
"@anticrm/notification": "~0.6.0",
"@anticrm/notification-assets": "~0.6.0",
"@anticrm/notification-resources": "~0.6.0",
"@anticrm/core": "~0.6.16",
"@anticrm/rekoni": "~0.6.0"
+2
View File
@@ -19,6 +19,7 @@ import login from '@anticrm/login'
import { clientId } from '@anticrm/client'
import { serverAttachmentId } from '@anticrm/server-attachment'
import { serverContactId } from '@anticrm/server-contact'
import { serverNotificationId } from '@anticrm/server-notification'
import { setMetadata } from '@anticrm/platform'
@@ -33,6 +34,7 @@ export function configurePlatformDev() {
addLocation(serverAttachmentId, () => import(/* webpackChunkName: "server-attachment" */ '@anticrm/server-attachment-resources'))
addLocation(serverContactId, () => import(/* webpackChunkName: "server-contact" */ '@anticrm/server-contact-resources'))
addLocation(serverNotificationId, () => import(/* webpackChunkName: "server-notification" */ '@anticrm/server-notification-resources'))
// Set devmodel to hook client to be able to present all activity
enableDevModel()
+1
View File
@@ -51,6 +51,7 @@ import '@anticrm/gmail-assets'
import '@anticrm/workbench-assets'
import '@anticrm/inventory-assets'
import '@anticrm/templates-assets'
import '@anticrm/notification-assets'
import { setMetadata } from '@anticrm/platform'
export async function configurePlatform() {
+2
View File
@@ -73,6 +73,8 @@
"@anticrm/attachment": "~0.6.1",
"@anticrm/server-contact": "~0.6.1",
"@anticrm/server-contact-resources": "~0.6.0",
"@anticrm/server-notification": "~0.6.0",
"@anticrm/server-notification-resources": "~0.6.0",
"@anticrm/server-tool": "~0.6.0"
}
}
+2
View File
@@ -49,6 +49,7 @@ import {
} from '@anticrm/server-core'
import { serverAttachmentId } from '@anticrm/server-attachment'
import { serverContactId } from '@anticrm/server-contact'
import { serverNotificationId } from '@anticrm/server-notification'
import { Client as ElasticClient } from '@elastic/elasticsearch'
import { Client } from 'minio'
import { Db, MongoClient } from 'mongodb'
@@ -104,6 +105,7 @@ export class ElasticTool {
constructor (readonly mongoUrl: string, readonly dbName: string, readonly minio: Client, readonly elasticUrl: string) {
addLocation(serverAttachmentId, () => import('@anticrm/server-attachment-resources'))
addLocation(serverContactId, () => import('@anticrm/server-contact-resources'))
addLocation(serverNotificationId, () => import('@anticrm/server-notification-resources'))
this.mongoClient = new MongoClient(mongoUrl)
}
+1
View File
@@ -45,6 +45,7 @@
"@anticrm/model-server-core": "~0.6.0",
"@anticrm/model-server-attachment": "~0.6.0",
"@anticrm/model-server-contact": "~0.6.0",
"@anticrm/model-server-notification": "~0.6.0",
"@anticrm/model-activity": "~0.6.0",
"@anticrm/model-attachment": "~0.6.0",
"@anticrm/model-gmail": "~0.6.0",
+2 -1
View File
@@ -30,6 +30,7 @@ import { createModel as presentationModel } from '@anticrm/model-presentation'
import { createModel as recruitModel } from '@anticrm/model-recruit'
import { createModel as serverAttachmentModel } from '@anticrm/model-server-attachment'
import { createModel as serverContactModel } from '@anticrm/model-server-contact'
import { createModel as serverNotificationModel } from '@anticrm/model-server-notification'
import { createModel as serverCoreModel } from '@anticrm/model-server-core'
import { createModel as settingModel } from '@anticrm/model-setting'
import { createModel as taskModel } from '@anticrm/model-task'
@@ -66,7 +67,7 @@ const builders = [
serverCoreModel,
serverAttachmentModel,
serverContactModel,
serverNotificationModel,
createDemo
]
+1
View File
@@ -27,6 +27,7 @@
"dependencies": {
"@anticrm/core": "~0.6.11",
"@anticrm/model": "~0.6.0",
"@anticrm/ui": "~0.6.0",
"@anticrm/platform": "~0.6.5",
"@anticrm/model-core": "~0.6.0",
"@anticrm/notification": "~0.6.0"
+16 -6
View File
@@ -14,23 +14,33 @@
// limitations under the License.
//
import type { Account, Domain, Ref, Timestamp } from '@anticrm/core'
import { Builder, Model, Prop, TypeRef, TypeTimestamp } from '@anticrm/model'
import type { Account, Doc, Domain, Ref, Timestamp, TxCUD } from '@anticrm/core'
import { Builder, Model, Prop, TypeRef, TypeString, TypeTimestamp } from '@anticrm/model'
import core, { TAttachedDoc } from '@anticrm/model-core'
import notificaton, { LastView } from '@anticrm/notification'
import type { LastView, Notification, NotificationStatus } from '@anticrm/notification'
import notificaton from './plugin'
import type { IntlString } from '@anticrm/platform'
export const DOMAIN_NOTIFICATION = 'notification' as Domain
@Model(notificaton.class.LastView, core.class.AttachedDoc, DOMAIN_NOTIFICATION)
export class TLastView extends TAttachedDoc implements LastView {
@Prop(TypeTimestamp(), 'Last View' as IntlString)
@Prop(TypeTimestamp(), notificaton.string.LastView)
lastView!: Timestamp
@Prop(TypeRef(core.class.Account), 'Modified By' as IntlString)
user!: Ref<Account>
}
export function createModel (builder: Builder): void {
builder.createModel(TLastView)
@Model(notificaton.class.Notification, core.class.AttachedDoc, DOMAIN_NOTIFICATION)
export class TNotification extends TAttachedDoc implements Notification {
@Prop(TypeRef(core.class.Tx), 'TX' as IntlString)
tx!: Ref<TxCUD<Doc>>
@Prop(TypeString(), 'Status' as IntlString)
status!: NotificationStatus
}
export function createModel (builder: Builder): void {
builder.createModel(TLastView, TNotification)
}
+25
View File
@@ -0,0 +1,25 @@
//
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021, 2022 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
//
import { IntlString, mergeIds } from '@anticrm/platform'
import notification, { notificationId } from '@anticrm/notification'
import {} from '@anticrm/ui'
export default mergeIds(notificationId, notification, {
string: {
LastView: '' as IntlString
}
})
+7
View File
@@ -0,0 +1,7 @@
module.exports = {
extends: ['./node_modules/@anticrm/model-rig/profiles/default/config/eslint.config.json'],
parserOptions: {
tsconfigRootDir: __dirname,
project: './tsconfig.json'
}
}
@@ -0,0 +1,18 @@
// The "rig.json" file directs tools to look for their config files in an external package.
// Documentation for this system: https://www.npmjs.com/package/@rushstack/rig-package
{
"$schema": "https://developer.microsoft.com/json-schemas/rig-package/rig.schema.json",
/**
* (Required) The name of the rig package to inherit from.
* It should be an NPM package name with the "-rig" suffix.
*/
"rigPackageName": "@anticrm/model-rig"
/**
* (Optional) Selects a config profile from the rig package. The name must consist of
* lowercase alphanumeric words separated by hyphens, for example "sample-profile".
* If omitted, then the "default" profile will be used."
*/
// "rigProfile": "your-profile-name"
}
+34
View File
@@ -0,0 +1,34 @@
{
"name": "@anticrm/model-server-notification",
"version": "0.6.0",
"main": "lib/index.js",
"author": "Anticrm Platform Contributors",
"license": "EPL-2.0",
"scripts": {
"build": "heft build",
"build:watch": "tsc",
"lint:fix": "eslint --fix src",
"lint": "eslint src",
"format": "prettier --write src && eslint --fix src"
},
"devDependencies": {
"@anticrm/model-rig": "~0.6.0",
"@typescript-eslint/eslint-plugin": "^5.4.0",
"eslint-plugin-import": "^2.25.3",
"eslint-plugin-promise": "^5.1.1",
"eslint-plugin-node": "^11.1.0",
"eslint": "^7.32.0",
"@types/heft-jest": "^1.0.2",
"@typescript-eslint/parser": "^5.4.0",
"eslint-config-standard-with-typescript": "^21.0.1",
"prettier": "^2.4.1",
"@rushstack/heft": "^0.41.1"
},
"dependencies": {
"@anticrm/core": "~0.6.11",
"@anticrm/model": "~0.6.0",
"@anticrm/platform": "~0.6.5",
"@anticrm/server-notification": "~0.6.0",
"@anticrm/server-core": "~0.6.0"
}
}
+27
View File
@@ -0,0 +1,27 @@
//
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021, 2022 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
//
import { Builder } from '@anticrm/model'
import serverCore from '@anticrm/server-core'
import core from '@anticrm/core'
import serverNotification from '@anticrm/server-notification'
export function createModel (builder: Builder): void {
builder.createDoc(serverCore.class.Trigger, core.space.Model, {
trigger: serverNotification.trigger.OnBacklinkCreate
})
}
+8
View File
@@ -0,0 +1,8 @@
{
"extends": "./node_modules/@anticrm/model-rig/profiles/default/tsconfig.json",
"compilerOptions": {
"rootDir": "./src",
"outDir": "./lib",
}
}
+1 -2
View File
@@ -40,7 +40,6 @@
"@anticrm/text-editor": "~0.6.0",
"@anticrm/contact": "~0.6.2",
"@anticrm/view": "~0.6.0",
"@anticrm/view-resources": "~0.6.0",
"@anticrm/chunter-resources": "~0.6.0"
"@anticrm/view-resources": "~0.6.0"
}
}
+32 -30
View File
@@ -88,9 +88,9 @@ class ActivityImpl implements Activity {
private txes1: Array<TxCUD<Doc>> = []
private txes2: Array<TxCUD<Doc>> = []
constructor (readonly client: Client, attributes: Map<string, AnyAttribute>) {
this.hiddenAttributes = new Set([...attributes.entries()]
.filter(([, value]) => value.hidden === true)
.map(([key]) => key))
this.hiddenAttributes = new Set(
[...attributes.entries()].filter(([, value]) => value.hidden === true).map(([key]) => key)
)
this.txQuery1 = createQuery()
this.txQuery2 = createQuery()
}
@@ -118,7 +118,9 @@ class ActivityImpl implements Activity {
? { 'tx.objectId': object._id as Ref<AttachedDoc> }
: {
objectId: object._id,
_class: { $in: [core.class.TxCreateDoc, core.class.TxUpdateDoc, core.class.TxRemoveDoc, core.class.TxMixin] }
_class: {
$in: [core.class.TxCreateDoc, core.class.TxUpdateDoc, core.class.TxRemoveDoc, core.class.TxMixin]
}
},
(result) => {
this.txes1 = result
@@ -230,7 +232,7 @@ class ActivityImpl implements Activity {
collectionCUD = true
}
let firstTx = parents.get(tx.objectId)
const result: DisplayTx = this.newDisplayTx(tx)
const result: DisplayTx = newDisplayTx(tx, hierarchy)
result.doc = firstTx?.doc ?? result.doc
@@ -273,34 +275,19 @@ class ActivityImpl implements Activity {
return false
}
newDisplayTx (tx: TxCUD<Doc>): DisplayTx {
const hierarchy = this.client.getHierarchy()
const createTx = hierarchy.isDerived(tx._class, core.class.TxCreateDoc) ? (tx as TxCreateDoc<Doc>) : undefined
return {
tx,
txes: [],
createTx,
updateTx: hierarchy.isDerived(tx._class, core.class.TxUpdateDoc) ? (tx as TxUpdateDoc<Doc>) : undefined,
updated: false,
removed: false,
mixin: false,
mixinTx: hierarchy.isDerived(tx._class, core.class.TxMixin) ? (tx as TxMixin<Doc, Doc>) : undefined,
doc: createTx !== undefined ? TxProcessor.createDoc2Doc(createTx) : undefined
}
}
integrateTxWithResults (results: DisplayTx[], result: DisplayTx): DisplayTx[] {
const curUpdate: any = (result.tx._class === core.class.TxUpdateDoc)
? (result.tx as unknown as TxUpdateDoc<Doc>).operations
: (result.tx as unknown as TxMixin<Doc, Doc>).attributes
const curUpdate: any =
result.tx._class === core.class.TxUpdateDoc
? (result.tx as unknown as TxUpdateDoc<Doc>).operations
: (result.tx as unknown as TxMixin<Doc, Doc>).attributes
const newResult = results.filter((prevTx) => {
if (this.isSameKindTx(prevTx, result, result.tx._class)) {
const prevUpdate: any = (prevTx.tx._class === core.class.TxUpdateDoc)
? (prevTx.tx as unknown as TxUpdateDoc<Doc>).operations
: (prevTx.tx as unknown as TxMixin<Doc, Doc>).attributes
if (
result.tx.modifiedOn - prevTx.tx.modifiedOn < combineThreshold && isEqualOps(prevUpdate, curUpdate) ) {
const prevUpdate: any =
prevTx.tx._class === core.class.TxUpdateDoc
? (prevTx.tx as unknown as TxUpdateDoc<Doc>).operations
: (prevTx.tx as unknown as TxMixin<Doc, Doc>).attributes
if (result.tx.modifiedOn - prevTx.tx.modifiedOn < combineThreshold && isEqualOps(prevUpdate, curUpdate)) {
// we have same keys,
// Remember previous transactions
result.txes.push(...prevTx.txes, prevTx.tx)
@@ -324,7 +311,22 @@ class ActivityImpl implements Activity {
}
}
function getCollectionTx (cltx: TxCollectionCUD<Doc, AttachedDoc>): TxCUD<Doc> {
export function newDisplayTx (tx: TxCUD<Doc>, hierarchy: Hierarchy): DisplayTx {
const createTx = hierarchy.isDerived(tx._class, core.class.TxCreateDoc) ? (tx as TxCreateDoc<Doc>) : undefined
return {
tx,
txes: [],
createTx,
updateTx: hierarchy.isDerived(tx._class, core.class.TxUpdateDoc) ? (tx as TxUpdateDoc<Doc>) : undefined,
updated: false,
removed: false,
mixin: false,
mixinTx: hierarchy.isDerived(tx._class, core.class.TxMixin) ? (tx as TxMixin<Doc, Doc>) : undefined,
doc: createTx !== undefined ? TxProcessor.createDoc2Doc(createTx) : undefined
}
}
export function getCollectionTx (cltx: TxCollectionCUD<Doc, AttachedDoc>): TxCUD<Doc> {
if (cltx.tx._class === core.class.TxCreateDoc) {
// We need to update tx to contain attachedDoc, attachedClass & collection
const create = cltx.tx as TxCreateDoc<AttachedDoc>
@@ -15,10 +15,10 @@
-->
<script lang="ts">
import activity, { TxViewlet } from '@anticrm/activity'
import { CommentInput } from '@anticrm/chunter-resources'
import chunter from '@anticrm/chunter'
import { Doc, SortingOrder } from '@anticrm/core'
import { createQuery, getClient } from '@anticrm/presentation'
import { Grid, IconActivity, Scroller } from '@anticrm/ui'
import { Component, Grid, IconActivity, Scroller } from '@anticrm/ui'
import { ActivityKey, activityKey, DisplayTx, newActivity } from '../activity'
import TxView from './TxView.svelte'
@@ -50,7 +50,7 @@
</script>
{#if fullSize || transparent}
{#if transparent !== undefined && !transparent}
{#if transparent !== undefined && !transparent}
<div class="ac-header short mirror-tool divide">
<div class="ac-header__wrap-title">
<div class="ac-header__icon flex-center icon"><IconActivity size={'small'} /></div>
@@ -64,14 +64,17 @@
{#if txes}
<Grid column={1} rowGap={1.5}>
{#each txes as tx (tx.tx._id)}
<TxView {tx} {viewlets} />
<TxView
{tx}
{viewlets}
/>
{/each}
</Grid>
{/if}
</div>
</Scroller>
<div class="ref-input">
<CommentInput bind:object/>
<Component is={chunter.component.CommentInput} props={{ object }} />
</div>
</div>
{:else}
@@ -98,7 +101,7 @@
</div>
</Scroller>
<div class="ref-input fill">
<CommentInput bind:object/>
<Component is={chunter.component.CommentInput} props={{ object }} />
</div>
{/if}
@@ -115,10 +118,18 @@
flex-shrink: 0;
padding: 1.5rem 2.5rem;
&.fill { background-color: var(--theme-bg-accent-normal); }
&.fill {
background-color: var(--theme-bg-accent-normal);
}
}
.p-activity { padding: 1.5rem 2.5rem 2.5rem; }
.scroller-back { background-color: var(--theme-bg-accent-normal); }
:global(.grid .msgactivity-container:last-child::after) { content: none; } // Remove the line in the last Activity message
.p-activity {
padding: 1.5rem 2.5rem 2.5rem;
}
.scroller-back {
background-color: var(--theme-bg-accent-normal);
}
:global(.grid .msgactivity-container:last-child::after) {
content: none;
} // Remove the line in the last Activity message
</style>
@@ -13,7 +13,6 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-->
<script lang="ts">
import type { TxViewlet } from '@anticrm/activity'
import activity from '@anticrm/activity'
@@ -21,15 +20,7 @@
import core, { AnyAttribute, Doc, Ref } from '@anticrm/core'
import { Asset, getResource } from '@anticrm/platform'
import { getClient } from '@anticrm/presentation'
import {
Component,
Icon,
IconEdit,
IconMoreH,
Label,
Menu, ShowMore, showPopup,
TimeSince
} from '@anticrm/ui'
import { Component, Icon, IconEdit, IconMoreH, Label, Menu, ShowMore, showPopup, TimeSince } from '@anticrm/ui'
import type { AttributeModel } from '@anticrm/view'
import { getActions } from '@anticrm/view-resources'
import { ActivityKey, DisplayTx } from '../activity'
@@ -37,7 +28,7 @@
export let tx: DisplayTx
export let viewlets: Map<ActivityKey, TxViewlet>
export let showIcon: boolean = true
let ptx: DisplayTx | undefined
@@ -74,7 +65,6 @@
employee = account
})
const showMenu = async (ev: MouseEvent): Promise<void> => {
const actions = await getActions(client, tx.doc as Doc)
showPopup(
@@ -110,25 +100,24 @@
return attr?.type._class === core.class.TypeMarkup
}
$: hasMessageType = model.find(m => isMessageType(m.attribute))
$: hasMessageType = model.find((m) => isMessageType(m.attribute))
</script>
{#if (viewlet !== undefined && !((viewlet?.hideOnRemove ?? false) && tx.removed)) || model.length > 0}
<div class="flex-between msgactivity-container">
<div class="flex-center icon">
{#if viewlet}
<Icon icon={viewlet.icon} size="small" />
{:else}
{#if viewlet === undefined && model.length > 0}
{#if (viewlet !== undefined && !((viewlet?.hideOnRemove ?? false) && tx.removed)) || model.length > 0}
<div class="flex-between msgactivity-container" class:showIcon>
{#if showIcon}
<div class="flex-center icon">
{#if viewlet}
<Icon icon={viewlet.icon} size="small" />
{:else if viewlet === undefined && model.length > 0}
<Icon icon={modelIcon !== undefined ? modelIcon : IconEdit} size="small" />
{:else}
<Icon icon={activity.icon.Activity} size="small" />
{/if}
{/if}
</div>
</div>
{/if}
<div class="flex-grow flex-col">
<div class="flex-between">
<div class="flex-grow label">
<div class="bold">
@@ -141,7 +130,7 @@
{#if viewlet && viewlet?.editable}
<div class="edited">
{#if viewlet.label}
<Label label={viewlet.label} params={viewlet.labelParams ?? {}} />
<Label label={viewlet.label} params={viewlet.labelParams ?? {}} />
{/if}
{#if tx.updated}
<Label label={activity.string.Edited} />
@@ -151,53 +140,56 @@
</div>
</div>
{:else if viewlet && viewlet.label}
<div class='flex-center'>
<div class="flex-center">
<Label label={viewlet.label} params={viewlet.labelParams ?? {}} />
{#if viewlet.labelComponent}
<Component is={viewlet.labelComponent} {props} />
<Component
is={viewlet.labelComponent}
{props}
/>
{/if}
</div>
{/if}
{#if viewlet === undefined && model.length > 0 && tx.updateTx}
{#if viewlet === undefined && model.length > 0 && tx.updateTx}
{#each model as m, i}
{#await getValue(client, m, tx.updateTx.operations) then value}
{#if value === null}
<span>unset <Label label={m.label} /></span>
{:else}
<span class:flex-grow={hasMessageType}>changed <Label label={m.label} /> to</span>
{#if hasMessageType}
<div class="time"><TimeSince value={tx.tx.modifiedOn} /></div>
{/if}
{#if isMessageType(m.attribute)}
<div class="strong message emphasized">
<svelte:component this={m.presenter} {value} />
</div>
{:else}
<div class="strong">
<svelte:component this={m.presenter} {value} />
</div>
{/if}
{#if value === null}
<span>unset <Label label={m.label} /></span>
{:else}
<span class:flex-grow={hasMessageType}>changed <Label label={m.label} /> to</span>
{#if hasMessageType}
<div class="time"><TimeSince value={tx.tx.modifiedOn} /></div>
{/if}
{/await}
{#if isMessageType(m.attribute)}
<div class="strong message emphasized">
<svelte:component this={m.presenter} {value} />
</div>
{:else}
<div class="strong">
<svelte:component this={m.presenter} {value} />
</div>
{/if}
{/if}
{/await}
{/each}
{:else if viewlet === undefined && model.length > 0 && tx.mixinTx}
{#each model as m}
{#await getValue(client, m, tx.mixinTx.attributes) then value}
{#if value === null}
<span>unset <Label label={m.label} /></span>
{#if value === null}
<span>unset <Label label={m.label} /></span>
{:else}
<span>changed <Label label={m.label} /> to</span>
{#if isMessageType(m.attribute)}
<div class="strong message emphasized">
<svelte:component this={m.presenter} {value} />
</div>
{:else}
<span>changed <Label label={m.label} /> to</span>
{#if isMessageType(m.attribute)}
<div class="strong message emphasized">
<svelte:component this={m.presenter} {value} />
</div>
{:else}
<div class="strong">
<svelte:component this={m.presenter} {value} />
</div>
{/if}
<div class="strong">
<svelte:component this={m.presenter} {value} />
</div>
{/if}
{/await}
{/if}
{/await}
{/each}
{:else if viewlet && viewlet.display === 'inline' && viewlet.component}
{#if typeof viewlet.component === 'string'}
@@ -230,6 +222,9 @@
<style lang="scss">
.msgactivity-container {
position: relative;
}
.showIcon {
&::after,
&::before {
position: absolute;
@@ -252,10 +247,12 @@
}
.menuOptions {
margin-left: .5rem;
opacity: .8;
margin-left: 0.5rem;
opacity: 0.8;
cursor: pointer;
&:hover { opacity: 1; }
&:hover {
opacity: 1;
}
}
.icon {
flex-shrink: 0;
@@ -279,8 +276,12 @@
align-items: center;
flex-wrap: wrap;
& > * { margin-right: .5rem; }
& > *:last-child { margin-right: 0; }
& > * {
margin-right: 0.5rem;
}
& > *:last-child {
margin-right: 0;
}
.bold {
font-weight: 500;
color: var(--theme-caption-color);
@@ -299,14 +300,14 @@
.content {
flex-shrink: 0;
margin-top: .5rem;
margin-top: 0.5rem;
}
.emphasized {
margin-top: .5rem;
margin-top: 0.5rem;
background-color: var(--theme-bg-accent-color);
border: 1px solid var(--theme-bg-accent-color);
border-radius: .75rem;
border-radius: 0.75rem;
padding: 1rem 1.25rem;
}
+5
View File
@@ -15,6 +15,11 @@
import { Resources } from '@anticrm/platform'
import Activity from './components/Activity.svelte'
import TxView from './components/TxView.svelte'
export { TxView }
export * from './activity'
export default async (): Promise<Resources> => ({
component: {
@@ -13,34 +13,36 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-->
<script lang="ts">
import type { Channel } from '@anticrm/chunter'
import { Ref, Space } from '@anticrm/core'
import { getClient } from '@anticrm/presentation'
import { closePopup, getCurrentLocation, Icon, navigate } from '@anticrm/ui'
import { getCurrentLocation, Icon, navigate } from '@anticrm/ui'
import chunter from '../plugin'
export let value: Channel
const client = getClient()
$: icon = client.getHierarchy().getClass(value._class).icon
function selectSpace (id: Ref<Space>) {
closePopup()
const loc = getCurrentLocation()
loc.path[1] = chunter.app.Chunter
loc.path[2] = id
loc.path.length = 3
loc.fragment = undefined
navigate(loc)
}
</script>
<div class="flex-row-center hover-trans" on:click={() => {
selectSpace(value._id)
}}>
<div
class="flex-row-center hover-trans"
on:click={() => {
selectSpace(value._id)
}}
>
{#if icon}
<Icon icon={icon} size={'small'}/>
<Icon {icon} size={'small'} />
{/if}
{value.name}
</div>
@@ -12,7 +12,6 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-->
<script lang="ts">
import type { Backlink } from '@anticrm/chunter'
import type { Doc } from '@anticrm/core'
@@ -30,12 +29,14 @@
const docQuery = createQuery()
let doc: Doc | undefined
$: docQuery.query(value.backlinkClass, { _id: value.backlinkId }, (r) => { doc = r.shift() })
$: docQuery.query(value.backlinkClass, { _id: value.backlinkId }, (r) => {
doc = r.shift()
})
$: className = client.getHierarchy().getClass(value.attachedToClass).label.toLocaleLowerCase()
$: if (doc !== undefined) {
getObjectPresenter(client, doc._class, { key: '' }).then(p => {
getObjectPresenter(client, doc._class, { key: '' }).then((p) => {
presenter = p
})
}
@@ -44,6 +45,6 @@
{#if presenter}
{className} in
<div class="ml-2">
<svelte:component this={presenter.presenter} value={doc}/>
<svelte:component this={presenter.presenter} value={doc} />
</div>
{/if}
+2 -1
View File
@@ -25,10 +25,11 @@ import CommentPresenter from './components/CommentPresenter.svelte'
import CommentsPresenter from './components/CommentsPresenter.svelte'
import CreateChannel from './components/CreateChannel.svelte'
export { CommentsPresenter, CommentInput }
export { CommentsPresenter }
export default async (): Promise<Resources> => ({
component: {
CommentInput,
CreateChannel,
ChannelView,
CommentPresenter,
+1
View File
@@ -27,6 +27,7 @@
},
"dependencies": {
"@anticrm/platform": "~0.6.5",
"@anticrm/ui": "~0.6.0",
"@anticrm/core": "~0.6.11"
}
}
+4
View File
@@ -16,6 +16,7 @@
import { IntlString, plugin } from '@anticrm/platform'
import type { Asset, Plugin } from '@anticrm/platform'
import type { Space, Doc, Ref, Class, AttachedDoc } from '@anticrm/core'
import { AnyComponent } from '@anticrm/ui'
/**
* @public
@@ -64,6 +65,9 @@ export default plugin(chunterId, {
Hashtag: '' as Asset,
Lock: '' as Asset
},
component: {
CommentInput: '' as AnyComponent
},
class: {
Message: '' as Ref<Class<Message>>,
Backlink: '' as Ref<Class<Backlink>>,
@@ -15,15 +15,15 @@
-->
<script lang="ts">
import { Product } from '@anticrm/inventory'
import { closeTooltip, Icon, showPanel } from '@anticrm/ui'
import { Icon, showPanel } from '@anticrm/ui'
import view from '@anticrm/view'
import inventory from '../plugin'
export let value: Product
export let inline: boolean = false
function show () {
closeTooltip()
showPanel(view.component.EditDoc, value._id, value._class, 'full')
}
</script>
@@ -15,14 +15,13 @@
-->
<script lang="ts">
import type { Lead } from '@anticrm/lead'
import { closeTooltip, Icon, showPanel } from '@anticrm/ui'
import { Icon, showPanel } from '@anticrm/ui'
import view from '@anticrm/view'
import lead from '../plugin'
export let value: Lead
function show () {
closeTooltip()
showPanel(view.component.EditDoc, value._id, value._class, 'full')
}
</script>
+7
View File
@@ -0,0 +1,7 @@
module.exports = {
extends: ['./node_modules/@anticrm/platform-rig/profiles/default/config/eslint.config.json'],
parserOptions: {
tsconfigRootDir: __dirname,
project: './tsconfig.json'
}
}
@@ -0,0 +1,5 @@
<svg xmlns="http://www.w3.org/2000/svg" style="display: none;">
<symbol id="notification" viewBox="0 0 24 24">
<path d="M9.78261 18.7959C9.78261 20.0132 10.7754 21 12 21C13.2246 21 14.2174 20.0132 14.2174 18.7959M19.3905 14.7551C18.7778 14.7551 18.2826 14.2631 18.2826 13.6524V9.24462C18.2826 5.79553 15.4703 3 12 3C8.52965 3 5.71739 5.79481 5.71739 9.24462V13.6524C5.71739 14.2609 5.2205 14.7551 4.60947 14.7551C3.99732 14.7551 3.5 15.2496 3.5 15.8571C3.5 16.4658 3.99753 16.9592 4.61235 16.9592H19.3876C20.0015 16.9592 20.5 16.4646 20.5 15.8571C20.5 15.2497 20.0014 14.7551 19.3905 14.7551Z"/>
</symbol>
</svg>

After

Width:  |  Height:  |  Size: 621 B

+8
View File
@@ -0,0 +1,8 @@
{
"string": {
"LastView": "Last View",
"Notification": "Notification",
"Notifications": "Notifications",
"NoNotifications": "No notifications"
}
}
+33
View File
@@ -0,0 +1,33 @@
{
"name": "@anticrm/notification-assets",
"version": "0.6.0",
"main": "lib/index.js",
"author": "Anticrm Platform Contributors",
"license": "EPL-2.0",
"scripts": {
"build": "heft build",
"build:docs": "",
"lint": "eslint src",
"lint:fix": "eslint --fix src",
"format": "prettier --write src && eslint --fix src",
"build:watch": "tsc"
},
"devDependencies": {
"@anticrm/platform-rig": "~0.6.0",
"@types/heft-jest": "^1.0.2",
"@typescript-eslint/eslint-plugin": "^5.4.0",
"@typescript-eslint/parser": "^5.4.0",
"eslint-config-standard-with-typescript": "^21.0.1",
"eslint-plugin-import": "^2.25.3",
"eslint-plugin-node": "^11.1.0",
"eslint-plugin-promise": "^5.1.1",
"eslint": "^7.32.0",
"prettier": "^2.4.1",
"@rushstack/heft": "^0.41.1",
"@types/node": "^16.4.10"
},
"dependencies": {
"@anticrm/platform": "~0.6.5",
"@anticrm/notification": "~0.6.0"
}
}
+24
View File
@@ -0,0 +1,24 @@
//
// Copyright © 2020 Anticrm Platform Contributors.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
//
import { loadMetadata, addStringsLoader } from '@anticrm/platform'
import notification, { notificationId } from '@anticrm/notification'
const icons = require('../assets/icons.svg') as string // eslint-disable-line
loadMetadata(notification.icon, {
Notifications: `${icons}#notification`
})
addStringsLoader(notificationId, async (lang: string) => await import(`../lang/${lang}.json`))
+15
View File
@@ -0,0 +1,15 @@
{
"compilerOptions": {
"moduleResolution": "node",
"target": "esnext",
"module": "esnext",
"declaration": true,
"outDir": "./lib",
"strict": true,
"esModuleInterop": true,
"lib": [
"esnext",
"dom"
]
}
}
+4 -4
View File
@@ -1,7 +1,7 @@
module.exports = {
extends: ['./node_modules/@anticrm/platform-rig/profiles/default/config/eslint.config.json'],
parserOptions: {
tsconfigRootDir: __dirname,
project: './tsconfig.json'
extends: ['./node_modules/@anticrm/platform-rig/profiles/ui/config/eslint.config.json'],
parserOptions: { tsconfigRootDir: __dirname },
settings: {
'svelte3/ignore-styles': () => true
}
}
+19 -17
View File
@@ -1,21 +1,23 @@
{
"name": "@anticrm/notification-resources",
"version": "0.6.0",
"main": "lib/index.js",
"main": "src/index.ts",
"author": "Anticrm Platform Contributors",
"template": "@anticrm/platform-package",
"license": "EPL-2.0",
"scripts": {
"build": "heft build",
"build:watch": "tsc",
"build": "echo 'no build for ui'",
"build:docs": "api-extractor run --local",
"lint": "svelte-check && eslint",
"lint:fix": "eslint --fix src",
"lint": "eslint src",
"format": "prettier --write src && eslint --fix src",
"format": "prettier --write --plugin-search-dir=. src && eslint --fix src",
"svelte-check": "svelte-check"
},
"devDependencies": {
"@anticrm/platform-rig": "~0.6.0",
"@types/heft-jest": "^1.0.2",
"svelte-loader": "^3.1.2",
"sass": "^1.37.5",
"svelte-preprocess": "^4.7.4",
"@typescript-eslint/eslint-plugin": "^5.4.0",
"eslint-plugin-import": "^2.25.3",
"eslint-plugin-promise": "^5.1.1",
@@ -23,21 +25,21 @@
"eslint": "^7.32.0",
"@typescript-eslint/parser": "^5.4.0",
"eslint-config-standard-with-typescript": "^21.0.1",
"prettier": "^2.4.1",
"@rushstack/heft": "^0.41.1",
"typescript": "^4.3.5",
"svelte-check": "^2.2.10",
"svelte-loader": "^3.1.2",
"sass": "^1.37.5",
"svelte-preprocess": "^4.7.4",
"eslint-plugin-svelte3": "~3.2.1",
"prettier-plugin-svelte": "^2.2.0"
"prettier-plugin-svelte": "^2.2.0",
"prettier": "^2.4.1",
"svelte-check": "^2.2.10",
"typescript": "^4.3.5"
},
"dependencies": {
"@anticrm/presentation": "~0.6.2",
"@anticrm/platform": "~0.6.5",
"@anticrm/core": "~0.6.11",
"svelte": "^3.37.0",
"@anticrm/notification": "~0.6.0",
"svelte": "^3.37.0"
"@anticrm/ui": "~0.6.0",
"@anticrm/presentation": "~0.6.2",
"@anticrm/activity-resources": "~0.6.0",
"@anticrm/activity": "~0.6.0",
"@anticrm/contact": "~0.6.0",
"@anticrm/core": "~0.6.11"
}
}
@@ -0,0 +1,73 @@
<!--
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021, 2022 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
-->
<script lang="ts">
import { TxViewlet } from '@anticrm/activity'
import { ActivityKey, DisplayTx, getCollectionTx, newDisplayTx, TxView } from '@anticrm/activity-resources'
import core, { AttachedDoc, Doc, TxCollectionCUD } from '@anticrm/core'
import { Notification, NotificationStatus } from '@anticrm/notification'
import { getClient } from '@anticrm/presentation'
export let notification: Notification
export let viewlets: Map<ActivityKey, TxViewlet>
const client = getClient()
const hierarchy = client.getHierarchy()
async function getDisplayTx (notification: Notification): Promise<DisplayTx | undefined> {
let tx = await client.findOne(core.class.TxCUD, { _id: notification.tx })
if (tx === undefined) return
if (hierarchy.isDerived(tx._class, core.class.TxCollectionCUD)) {
tx = getCollectionTx(tx as TxCollectionCUD<Doc, AttachedDoc>)
}
return newDisplayTx(tx, hierarchy)
}
async function read (notification: Notification): Promise<void> {
if (notification.status === NotificationStatus.Read) return
await client.updateDoc(notification._class, notification.space, notification._id, {
status: NotificationStatus.Read
})
}
</script>
{#await getDisplayTx(notification) then displayTx}
{#if displayTx}
<!-- svelte-ignore a11y-mouse-events-have-key-events -->
<div
class="content"
class:isNew={notification.status !== NotificationStatus.Read}
on:mouseover|once={() => {
read(notification)
}}
>
<TxView
tx={displayTx}
{viewlets}
showIcon={false}
/>
</div>
{/if}
{/await}
<style lang="scss">
.content {
padding: 0.5rem;
border-radius: 0.5rem;
border: 1px solid transparent;
}
.isNew {
border: 1px solid var(--theme-bg-focused-border);
}
</style>
@@ -0,0 +1,76 @@
<!--
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021, 2022 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
-->
<script lang="ts">
import activity, { TxViewlet } from '@anticrm/activity'
import { activityKey, ActivityKey } from '@anticrm/activity-resources'
import { EmployeeAccount } from '@anticrm/contact'
import { getCurrentAccount, SortingOrder } from '@anticrm/core'
import type { Notification } from '@anticrm/notification'
import { createQuery } from '@anticrm/presentation'
import { Grid } from '@anticrm/ui'
import Label from '@anticrm/ui/src/components/Label.svelte'
import notification from '../plugin'
import NotificationView from './NotificationView.svelte'
const query = createQuery()
let notifications: Notification[] = []
$: query.query(
notification.class.Notification,
{
attachedTo: (getCurrentAccount() as EmployeeAccount).employee
},
(res) => {
notifications = res
},
{
sort: { status: SortingOrder.Ascending, modifiedOn: SortingOrder.Descending }
}
)
let viewlets: Map<ActivityKey, TxViewlet>
const descriptors = createQuery()
$: descriptors.query(activity.class.TxViewlet, {}, (result) => {
viewlets = new Map(result.map((r) => [activityKey(r.objectClass, r.txClass), r]))
})
</script>
<div class="antiPopup popup">
<div class="ap-space" />
<div class="ap-scroll">
<div class="ap-box">
{#if notifications.length > 0}
<Grid column={1} rowGap={1.5}>
{#each notifications as n (n._id)}
<NotificationView notification={n} {viewlets} />
{/each}
</Grid>
{:else}
<Label label={notification.string.NoNotifications} />
{/if}
</div>
</div>
<div class="ap-space" />
</div>
<style lang="scss">
.popup {
max-width: 55rem;
padding: 0.75rem;
max-height: 35rem;
}
</style>
+7 -2
View File
@@ -15,7 +15,12 @@
//
import { Resources } from '@anticrm/platform'
export default async (): Promise<Resources> => ({})
import NotificationsPopup from './components/NotificationsPopup.svelte'
export * from './utils'
export default async (): Promise<Resources> => ({
component: {
NotificationsPopup
}
})
@@ -0,0 +1,26 @@
/*!
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021, 2022 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
*/
import type { IntlString } from '@anticrm/platform'
import { mergeIds } from '@anticrm/platform'
import notification, { notificationId } from '@anticrm/notification'
export default mergeIds(notificationId, notification, {
string: {
NoNotifications: '' as IntlString
}
})
+10 -3
View File
@@ -1,8 +1,15 @@
{
"extends": "./node_modules/@anticrm/platform-rig/profiles/default/tsconfig.json",
"compilerOptions": {
"rootDir": "./src",
"moduleResolution": "node",
"target": "esnext",
"module": "esnext",
"declaration": true,
"outDir": "./lib",
"strict": true,
"esModuleInterop": true,
"lib": [
"esnext",
"dom"
]
}
}
+2 -1
View File
@@ -27,6 +27,7 @@
},
"dependencies": {
"@anticrm/platform": "~0.6.5",
"@anticrm/core": "~0.6.11"
"@anticrm/core": "~0.6.11",
"@anticrm/ui": "~0.6.0"
}
}
+32 -3
View File
@@ -14,9 +14,10 @@
// limitations under the License.
//
import type { Account, AttachedDoc, Class, Ref, Space, Timestamp } from '@anticrm/core'
import type { Plugin } from '@anticrm/platform'
import type { Account, AttachedDoc, Class, Doc, Ref, Space, Timestamp, TxCUD } from '@anticrm/core'
import type { Asset, IntlString, Plugin } from '@anticrm/platform'
import { plugin } from '@anticrm/platform'
import { AnyComponent } from '@anticrm/ui'
/**
* @public
@@ -26,6 +27,23 @@ export interface LastView extends AttachedDoc {
user: Ref<Account>
}
/**
* @public
*/
export interface Notification extends AttachedDoc {
tx: Ref<TxCUD<Doc>>
status: NotificationStatus
}
/**
* @public
*/
export enum NotificationStatus {
New,
EmailSent,
Read
}
/**
* @public
*/
@@ -36,10 +54,21 @@ export const notificationId = 'notification' as Plugin
*/
const notification = plugin(notificationId, {
class: {
LastView: '' as Ref<Class<LastView>>
LastView: '' as Ref<Class<LastView>>,
Notification: '' as Ref<Class<Notification>>
},
component: {
NotificationsPopup: '' as AnyComponent
},
icon: {
Notifications: '' as Asset
},
space: {
Notifications: '' as Ref<Space>
},
string: {
Notification: '' as IntlString,
Notifications: '' as IntlString
}
})
@@ -17,7 +17,7 @@
import { getClient } from '@anticrm/presentation'
import type { Applicant } from '@anticrm/recruit'
import recruit from '@anticrm/recruit'
import { closeTooltip, Icon } from '@anticrm/ui'
import { Icon } from '@anticrm/ui'
import { showPanel } from '@anticrm/ui/src/panelup'
import view from '@anticrm/view'
@@ -27,7 +27,6 @@
const shortLabel = client.getHierarchy().getClass(value._class).shortLabel
function show () {
closeTooltip()
showPanel(view.component.EditDoc, value._id, value._class, 'full')
}
</script>
@@ -16,7 +16,7 @@
<script lang="ts">
import { getClient } from '@anticrm/presentation'
import type { Issue } from '@anticrm/task'
import { closeTooltip, Icon, showPanel } from '@anticrm/ui'
import { Icon, showPanel } from '@anticrm/ui'
import view from '@anticrm/view'
import task from '../plugin'
@@ -26,7 +26,6 @@
const shortLabel = client.getHierarchy().getClass(value._class).shortLabel
function show () {
closeTooltip()
showPanel(view.component.EditDoc, value._id, value._class, 'full')
}
</script>
@@ -133,7 +133,6 @@
$: if (object) getEditorOrDefault(selectedClass, object._class)
async function getEditorOrDefault (_class: Ref<Class<Doc>> | undefined, defaultClass: Ref<Class<Doc>>): Promise<void> {
console.log('get editor or default')
let editor = _class !== undefined ? await getEditor(_class) : undefined
if (editor === undefined) {
editor = await getEditor(defaultClass)
+1
View File
@@ -40,6 +40,7 @@
"@anticrm/presentation": "~0.6.2",
"@anticrm/login": "~0.6.1",
"@anticrm/setting": "~0.6.0",
"@anticrm/notification": "~0.6.0",
"@anticrm/contact": "~0.6.2",
"@anticrm/view-resources": "~0.6.0"
}
@@ -18,11 +18,15 @@
import { Avatar, createQuery, setClient } from '@anticrm/presentation'
import {
AnyComponent,
closePanel,
closePopup,
closeTooltip,
Component,
getCurrentLocation,
location,
navigate, PanelInstance, Popup,
navigate,
PanelInstance,
Popup,
showPopup,
TooltipInstance
} from '@anticrm/ui'
@@ -37,6 +41,7 @@
import NavHeader from './NavHeader.svelte'
import Navigator from './Navigator.svelte'
import SpaceView from './SpaceView.svelte'
import notification, { NotificationStatus } from '@anticrm/notification'
export let client: Client
@@ -54,6 +59,8 @@
onDestroy(
location.subscribe(async (loc) => {
closeTooltip()
closePopup()
if (currentApp !== loc.path[1]) {
currentApp = loc.path[1] as Ref<Application>
currentApplication = await client.findOne(workbench.class.Application, { _id: currentApp })
@@ -189,6 +196,23 @@
loc.path.length = 2
navigate(loc)
}
let hasNotification = false
const notificationQuery = createQuery()
$: notificationQuery.query(
notification.class.Notification,
{
attachedTo: (getCurrentAccount() as EmployeeAccount).employee,
status: { $in: [NotificationStatus.New, NotificationStatus.EmailSent] }
},
(res) => {
hasNotification = res.length > 0
},
{
limit: 1
}
)
</script>
{#if client}
@@ -214,19 +238,34 @@
notify={false}
/>
</div>
<Applications {apps} active={currentApp} on:active={(evt) => {
navigateApp(evt.detail)
}} />
<div class="flex-center" style="min-height: 6.25rem;">
<div
class="cursor-pointer"
on:click|stopPropagation={(el) => {
showPopup(AccountPopup, {}, 'account')
<Applications
{apps}
active={currentApp}
on:active={(evt) => {
navigateApp(evt.detail)
}}
/>
<div class="flex-row" style="margin-bottom: 2rem;">
<AppItem
icon={notification.icon.Notifications}
label={notification.string.Notifications}
selected={false}
action={async () => {
showPopup(notification.component.NotificationsPopup, {}, 'account')
}}
>
{#if employee}
<Avatar avatar={employee.avatar} size={'medium'} />
{/if}
notify={hasNotification}
/>
<div class="flex-center">
<div
class="cursor-pointer"
on:click|stopPropagation={(el) => {
showPopup(AccountPopup, {}, 'account')
}}
>
{#if employee}
<Avatar avatar={employee.avatar} size={'medium'} />
{/if}
</div>
</div>
</div>
</div>
@@ -72,7 +72,7 @@
<div>
<TreeNode label={model.label} actions={async () => [addSpace]}>
{#each spaces as space}
{#each spaces as space (space._id)}
<TreeItem
_id={space._id}
title={space.name}
+21 -1
View File
@@ -736,7 +736,7 @@
"projectFolder": "server/attachment-resources",
"shouldPublish": true
},
{
{
"packageName": "@anticrm/server-contact",
"projectFolder": "server/contact",
"shouldPublish": true
@@ -996,10 +996,30 @@
"projectFolder": "plugins/notification",
"shouldPublish": true
},
{
"packageName": "@anticrm/notification-assets",
"projectFolder": "plugins/notification-assets",
"shouldPublish": true
},
{
"packageName": "@anticrm/notification-resources",
"projectFolder": "plugins/notification-resources",
"shouldPublish": true
},
{
"packageName": "@anticrm/server-notification",
"projectFolder": "server/notification",
"shouldPublish": true
},
{
"packageName": "@anticrm/model-server-notification",
"projectFolder": "models/server-notification",
"shouldPublish": true
},
{
"packageName": "@anticrm/server-notification-resources",
"projectFolder": "server/notification-resources",
"shouldPublish": true
}
]
}
@@ -0,0 +1,7 @@
module.exports = {
extends: ['./node_modules/@anticrm/platform-rig/profiles/default/config/eslint.config.json'],
parserOptions: {
tsconfigRootDir: __dirname,
project: './tsconfig.json'
}
}
+4
View File
@@ -0,0 +1,4 @@
*
!/lib/**
!CHANGELOG.md
/lib/**/__tests__/
@@ -0,0 +1,18 @@
// The "rig.json" file directs tools to look for their config files in an external package.
// Documentation for this system: https://www.npmjs.com/package/@rushstack/rig-package
{
"$schema": "https://developer.microsoft.com/json-schemas/rig-package/rig.schema.json",
/**
* (Required) The name of the rig package to inherit from.
* It should be an NPM package name with the "-rig" suffix.
*/
"rigPackageName": "@anticrm/platform-rig"
/**
* (Optional) Selects a config profile from the rig package. The name must consist of
* lowercase alphanumeric words separated by hyphens, for example "sample-profile".
* If omitted, then the "default" profile will be used."
*/
// "rigProfile": "your-profile-name"
}
@@ -0,0 +1,36 @@
{
"name": "@anticrm/server-notification-resources",
"version": "0.6.0",
"main": "lib/index.js",
"author": "Anticrm Platform Contributors",
"license": "EPL-2.0",
"scripts": {
"build": "heft build",
"build:watch": "tsc",
"lint:fix": "eslint --fix src",
"lint": "eslint src",
"format": "prettier --write src && eslint --fix src"
},
"devDependencies": {
"@anticrm/platform-rig": "~0.6.0",
"@types/heft-jest": "^1.0.2",
"@typescript-eslint/eslint-plugin": "^5.4.0",
"eslint-plugin-import": "^2.25.3",
"eslint-plugin-promise": "^5.1.1",
"eslint-plugin-node": "^11.1.0",
"eslint": "^7.32.0",
"@typescript-eslint/parser": "^5.4.0",
"eslint-config-standard-with-typescript": "^21.0.1",
"prettier": "^2.4.1",
"@rushstack/heft": "^0.41.1",
"typescript": "^4.3.5"
},
"dependencies": {
"@anticrm/core": "~0.6.11",
"@anticrm/platform": "~0.6.5",
"@anticrm/server-core": "~0.6.0",
"@anticrm/notification": "~0.6.0",
"@anticrm/chunter": "~0.6.1",
"@anticrm/contact": "~0.6.4"
}
}
@@ -0,0 +1,71 @@
//
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021, 2022 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
//
import chunter, { Backlink } from '@anticrm/chunter'
import contact from '@anticrm/contact'
import core, { Data, Doc, generateId, Tx, TxCollectionCUD, TxCreateDoc } from '@anticrm/core'
import notification, { Notification, NotificationStatus } from '@anticrm/notification'
import type { TriggerControl } from '@anticrm/server-core'
/**
* @public
*/
export async function OnBacklinkCreate (tx: Tx, { findAll, hierarchy, storageFx }: TriggerControl): Promise<Tx[]> {
if (tx._class !== core.class.TxCollectionCUD) {
return []
}
const ptx = tx as TxCollectionCUD<Doc, Backlink>
if (
ptx.tx._class !== core.class.TxCreateDoc ||
!hierarchy.isDerived(ptx.tx.objectClass, chunter.class.Backlink) ||
!hierarchy.isDerived(ptx.objectClass, contact.class.Employee)
) {
return []
}
const createTx: TxCreateDoc<Notification> = {
objectClass: notification.class.Notification,
objectSpace: notification.space.Notifications,
objectId: generateId(),
modifiedOn: ptx.modifiedOn,
modifiedBy: ptx.modifiedBy,
space: ptx.space,
_id: generateId(),
_class: core.class.TxCreateDoc,
attributes: {
tx: ptx._id,
status: NotificationStatus.New
} as unknown as Data<Notification>
}
const result: TxCollectionCUD<Doc, Notification> = {
...ptx,
_id: generateId(),
collection: 'notifications',
tx: createTx
}
return [result]
}
// eslint-disable-next-line @typescript-eslint/explicit-function-return-type
export default async () => ({
trigger: {
OnBacklinkCreate
}
})
@@ -0,0 +1,8 @@
{
"extends": "./node_modules/@anticrm/platform-rig/profiles/default/tsconfig.json",
"compilerOptions": {
"rootDir": "./src",
"outDir": "./lib"
}
}
+7
View File
@@ -0,0 +1,7 @@
module.exports = {
extends: ['./node_modules/@anticrm/platform-rig/profiles/default/config/eslint.config.json'],
parserOptions: {
tsconfigRootDir: __dirname,
project: './tsconfig.json'
}
}
+4
View File
@@ -0,0 +1,4 @@
*
!/lib/**
!CHANGELOG.md
/lib/**/__tests__/
+18
View File
@@ -0,0 +1,18 @@
// The "rig.json" file directs tools to look for their config files in an external package.
// Documentation for this system: https://www.npmjs.com/package/@rushstack/rig-package
{
"$schema": "https://developer.microsoft.com/json-schemas/rig-package/rig.schema.json",
/**
* (Required) The name of the rig package to inherit from.
* It should be an NPM package name with the "-rig" suffix.
*/
"rigPackageName": "@anticrm/platform-rig"
/**
* (Optional) Selects a config profile from the rig package. The name must consist of
* lowercase alphanumeric words separated by hyphens, for example "sample-profile".
* If omitted, then the "default" profile will be used."
*/
// "rigProfile": "your-profile-name"
}
+34
View File
@@ -0,0 +1,34 @@
{
"name": "@anticrm/server-notification",
"version": "0.6.1",
"main": "lib/index.js",
"author": "Anticrm Platform Contributors",
"license": "EPL-2.0",
"scripts": {
"build": "heft build",
"build:watch": "tsc",
"lint:fix": "eslint --fix src",
"lint": "eslint src",
"format": "prettier --write src && eslint --fix src"
},
"devDependencies": {
"@anticrm/platform-rig": "~0.6.0",
"@types/heft-jest": "^1.0.2",
"@types/node": "^16.4.10",
"@typescript-eslint/eslint-plugin": "^5.4.0",
"eslint-plugin-import": "^2.25.3",
"eslint-plugin-promise": "^5.1.1",
"eslint-plugin-node": "^11.1.0",
"eslint": "^7.32.0",
"@typescript-eslint/parser": "^5.4.0",
"eslint-config-standard-with-typescript": "^21.0.1",
"prettier": "^2.4.1",
"@rushstack/heft": "^0.41.1",
"typescript": "^4.3.5"
},
"dependencies": {
"@anticrm/core": "~0.6.11",
"@anticrm/platform": "~0.6.5",
"@anticrm/server-core": "~0.6.0"
}
}
+33
View File
@@ -0,0 +1,33 @@
//
// Copyright © 2020, 2021 Anticrm Platform Contributors.
// Copyright © 2021, 2022 Hardcore Engineering Inc.
//
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License. You may
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
//
// See the License for the specific language governing permissions and
// limitations under the License.
//
import type { Resource, Plugin } from '@anticrm/platform'
import { plugin } from '@anticrm/platform'
import type { TriggerFunc } from '@anticrm/server-core'
/**
* @public
*/
export const serverNotificationId = 'server-notification' as Plugin
/**
* @public
*/
export default plugin(serverNotificationId, {
trigger: {
OnBacklinkCreate: '' as Resource<TriggerFunc>
}
})
+9
View File
@@ -0,0 +1,9 @@
{
"extends": "./node_modules/@anticrm/platform-rig/profiles/default/tsconfig.json",
"compilerOptions": {
"rootDir": "./src",
"outDir": "./lib",
"esModuleInterop": true
}
}
+3 -1
View File
@@ -47,6 +47,8 @@
"elastic-apm-node": "~3.26.0",
"minio": "~7.0.26",
"@anticrm/server-contact": "~0.6.1",
"@anticrm/server-contact-resources": "~0.6.0"
"@anticrm/server-contact-resources": "~0.6.0",
"@anticrm/server-notification": "~0.6.0",
"@anticrm/server-notification-resources": "~0.6.0"
}
}
+2
View File
@@ -25,6 +25,7 @@ import { start as startJsonRpc } from '@anticrm/server-ws'
import { addLocation } from '@anticrm/platform'
import { serverAttachmentId } from '@anticrm/server-attachment'
import { serverContactId } from '@anticrm/server-contact'
import { serverNotificationId } from '@anticrm/server-notification'
import { metricsContext } from './metrics'
@@ -54,6 +55,7 @@ export interface MinioConfig {
export function start (dbUrl: string, fullTextUrl: string, minioConf: MinioConfig, port: number, host?: string): () => void {
addLocation(serverAttachmentId, () => import('@anticrm/server-attachment-resources'))
addLocation(serverContactId, () => import('@anticrm/server-contact-resources'))
addLocation(serverNotificationId, () => import('@anticrm/server-notification-resources'))
return startJsonRpc(metricsContext, (workspace: string) => {
const conf: DbConfiguration = {