mirror of
https://github.com/hcengineering/platform.git
synced 2026-09-22 01:25:00 +02:00
New card layout (#8796)
This commit is contained in:
Generated
+256
-196
@@ -35,29 +35,26 @@ importers:
|
||||
specifier: ^8.4.1
|
||||
version: 8.4.1
|
||||
'@hcengineering/communication-client-query':
|
||||
specifier: 0.1.172
|
||||
version: 0.1.172(typescript@5.3.3)
|
||||
specifier: 0.1.174
|
||||
version: 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-rest-client':
|
||||
specifier: 0.1.172
|
||||
version: 0.1.172(typescript@5.3.3)
|
||||
specifier: 0.1.174
|
||||
version: 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types':
|
||||
specifier: 0.1.172
|
||||
version: 0.1.172(typescript@5.3.3)
|
||||
specifier: 0.1.174
|
||||
version: 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-server':
|
||||
specifier: 0.1.172
|
||||
version: 0.1.172(typescript@5.3.3)
|
||||
specifier: 0.1.174
|
||||
version: 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared':
|
||||
specifier: 0.1.172
|
||||
version: 0.1.172(typescript@5.3.3)
|
||||
specifier: 0.1.174
|
||||
version: 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types':
|
||||
specifier: 0.1.172
|
||||
version: 0.1.172(typescript@5.3.3)
|
||||
specifier: 0.1.174
|
||||
version: 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-yaml':
|
||||
specifier: 0.1.172
|
||||
version: 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/drive':
|
||||
specifier: ^0.6.32
|
||||
version: 0.6.490
|
||||
specifier: 0.1.174
|
||||
version: 0.1.174(typescript@5.3.3)
|
||||
'@hocuspocus/provider':
|
||||
specifier: ^2.15.2
|
||||
version: 2.15.2(bufferutil@4.0.8)(utf-8-validate@6.0.4)(y-protocols@1.0.6(yjs@13.6.23))(yjs@13.6.23)
|
||||
@@ -226,6 +223,15 @@ importers:
|
||||
'@rush-temp/collaborator-client':
|
||||
specifier: file:./projects/collaborator-client.tgz
|
||||
version: file:projects/collaborator-client.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
'@rush-temp/communication':
|
||||
specifier: file:./projects/communication.tgz
|
||||
version: file:projects/communication.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
'@rush-temp/communication-assets':
|
||||
specifier: file:./projects/communication-assets.tgz
|
||||
version: file:projects/communication-assets.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
'@rush-temp/communication-resources':
|
||||
specifier: file:./projects/communication-resources.tgz
|
||||
version: file:projects/communication-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
'@rush-temp/contact':
|
||||
specifier: file:./projects/contact.tgz
|
||||
version: file:projects/contact.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
@@ -481,6 +487,9 @@ importers:
|
||||
'@rush-temp/model-chunter':
|
||||
specifier: file:./projects/model-chunter.tgz
|
||||
version: file:projects/model-chunter.tgz
|
||||
'@rush-temp/model-communication':
|
||||
specifier: file:./projects/model-communication.tgz
|
||||
version: file:projects/model-communication.tgz
|
||||
'@rush-temp/model-contact':
|
||||
specifier: file:./projects/model-contact.tgz
|
||||
version: file:projects/model-contact.tgz(encoding@0.1.13)
|
||||
@@ -2985,78 +2994,63 @@ packages:
|
||||
'@hcengineering/account-client@0.7.28':
|
||||
resolution: {integrity: sha512-k1dkioX+jYrLyAXLLLsBYVCdZKf3WjhnDHw/yeAQgLQQ/9W2ffLtDMZ8lYWV3XMQ3eWrUCodtTDOiAQgXd/LEQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/account-client/0.7.28/32c9bc0dd297f00f4d5461467f25e072d01b9c76}
|
||||
|
||||
'@hcengineering/analytics@0.6.490':
|
||||
resolution: {integrity: sha512-Jcdj9LXiIUxm75jRIaOrNlvTW48bd59ul2I0WB5NE3WHfAXKmk5FIBUd2dtTDhHMQUOZwUOKzVcxfYWIUs5HFQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/analytics/0.6.490/e2ed2bc32ca04e170e2907e6b0c44a3b725d36bd}
|
||||
|
||||
'@hcengineering/analytics@0.7.28':
|
||||
resolution: {integrity: sha512-+CI/wJ8zgop+3mEcvhlB1UJBU6tIKq2Y7qTichZjGli8BckEIEwbD4j2beu2qXRSoTT2yUGWM9zpS9+fmH/DAw==, tarball: https://npm.pkg.github.com/download/@hcengineering/analytics/0.7.28/a8faf3d575bb28b9682b659495e738f8e0ca596e}
|
||||
|
||||
'@hcengineering/card@0.7.28':
|
||||
resolution: {integrity: sha512-1d3allyx9jTpE/gr9kk/g5qo5848i4FKsRiHgCpJqzNEdRW7TAednoHAr2hKRU5DZC/i3Br56axSkUQzV2Idhg==, tarball: https://npm.pkg.github.com/download/@hcengineering/card/0.7.28/5348996f5b7b4a34517780a5bf324122cbddfbad}
|
||||
|
||||
'@hcengineering/communication-client-query@0.1.172':
|
||||
resolution: {integrity: sha512-LeSVl8zX/rnnVmfvuBN+klI3Jts1OxNdNEOsYJEgFDvGfK+dn3qmcLFUtqwJdh8y5tTGTBfqxn9LjZgCWOYZ8w==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-client-query/0.1.172/0cbf17add61d5932b6ce97c10b8de223e041b453}
|
||||
'@hcengineering/communication-client-query@0.1.174':
|
||||
resolution: {integrity: sha512-/JvTp99mkuxfNT853524Cs18kuO6JOF34RAnw/icEgWRAlmeVr0J2HqaQnUhqHiJYg7ZUCpjMVr/iF+rno0CoQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-client-query/0.1.174/a0ba56179280decedb3fb176fbe6f3aa9f5b902f}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-cockroach@0.1.172':
|
||||
resolution: {integrity: sha512-6RgvzAJ/n7tUjtJIb06jBUdl/k+nUbSuy3sh75ZNBwtNbE93CP+uJG9Wh/8vz416T1Z6hPxJENuVSzNcv9XEwQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-cockroach/0.1.172/cde6de8e8da5d3f239b4f5db4be6a194ffacacae}
|
||||
'@hcengineering/communication-cockroach@0.1.174':
|
||||
resolution: {integrity: sha512-+URXcZJ+Xz1r1HrIc2lRjS5a924dKX1g8p/igAJR0TQJO0Vm2k7kWf+8eUd/zqE7v/hiXnEOs5xLvqiwXw+RWA==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-cockroach/0.1.174/849e7081670ea824528e457c891a289d3fc56a9c}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-query@0.1.172':
|
||||
resolution: {integrity: sha512-EPuYWJ4s4T6ragx/29WpkM5YSqejnYBqwoFWX/2kUCOaV1kIZS2aFiuEz7IW3i6LUjrTt+EKz5EqOJXStqVY7Q==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-query/0.1.172/1c8a30191a4e233d759b01cf39af58531e9b52ca}
|
||||
'@hcengineering/communication-query@0.1.174':
|
||||
resolution: {integrity: sha512-KJE/wJYefOuMYjJ9TGKuc5R6WNoqzm60qm13VQAnbWozGttTz2+rhhhcd/kCDjtRyKfa1jBDwNA11ts/vnbKSw==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-query/0.1.174/a950b0c41d561b1a847acd459bf9028e6bde149e}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-rest-client@0.1.172':
|
||||
resolution: {integrity: sha512-z1rfFpNepm+13Dwaezf+4ni915F1wdocTIxqTVkLwAvfbC2SwxgW9aMSjfxsU/2nEW31XAosvAYFuM21R4uu6w==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-rest-client/0.1.172/4a221f95e64908eddb28aeedd7c7a7caed996aef}
|
||||
'@hcengineering/communication-rest-client@0.1.174':
|
||||
resolution: {integrity: sha512-U7Fj57DT30xTInL+JP5eTyhTBXMIL+DwyBaT1XtVH7g135dvNGmC/iGnHjJ1Cp30LYRuHf19ovoNvLbyFewnFw==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-rest-client/0.1.174/5c1b9744648628c532d9798412f7b62001a7d26e}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-sdk-types@0.1.172':
|
||||
resolution: {integrity: sha512-XeetCHsQjKE0AfqaXA/E1pqClxON6csb27I7bi+CTMOoVH6y3BejEREmI+rj28g/rxB6OdLAlchW4uxsqh+trA==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-sdk-types/0.1.172/5dbccb233f31dd7e8cf93e5d93858d50d0eb0a8a}
|
||||
'@hcengineering/communication-sdk-types@0.1.174':
|
||||
resolution: {integrity: sha512-cIiPLY0xM9GsISGBVol6R0kdX2ne50XYXkGKhbdpLyQM7SU9NrwxRwzHi1WV0UjHWmM0N0pGsgMKj8hKrBow4A==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-sdk-types/0.1.174/7a44ace6563f862c5c3479d32643fabdb6dccca9}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-server@0.1.172':
|
||||
resolution: {integrity: sha512-oOSqWFNNRks3pbYSZQG3oHWPLpBDXugRK47B0xec6aTdVvf+a688XHCdpkErFsbmqvazFwM/HwDIiWq/WfhqdA==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-server/0.1.172/7509a4e876a2f6d0023ed23a1c262baf434399ef}
|
||||
'@hcengineering/communication-server@0.1.174':
|
||||
resolution: {integrity: sha512-TT/fBmsVc7bSBGEZ7qxU9LibYqah61taI6ujvTzSDxXRspAvHIb4Jk4TtdyCcU/UzX8i2skUua0XbcPCcwAFpQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-server/0.1.174/5a575aebe3fbdc1a44d5a393cd47171b5c298da1}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-shared@0.1.172':
|
||||
resolution: {integrity: sha512-gPCcmxV9mlgScKQI7ENXlpxxA3v7gn6RpaL9toF/UmjCb63bvyShIt9Ti+P3rjm2KAZzutAhW5prSZwUlWHGjQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-shared/0.1.172/fc20f730b5bf0e8f7244fc4d2007bc71943c0c82}
|
||||
'@hcengineering/communication-shared@0.1.174':
|
||||
resolution: {integrity: sha512-P8lBufpX4psYU0emgjjSpSTWuyxI9FkuCUzdvav7bsDtZ7rAYjwSr/dOx7I51KPdxD2P9x6qHMQhEEsEc5isDg==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-shared/0.1.174/20e4eb0c34d263014cea37f424ed792e3946f6d5}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-types@0.1.172':
|
||||
resolution: {integrity: sha512-XeU5k09ONUFGPPpbfDOI8+uaUTJcxe+CH5UzpWPfMpOlF4+7Kx+TfCDCBiIc9CYSyedHZbtl+GZokmgGvhdajw==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-types/0.1.172/8a5f620e404dee92505900031dd3e804817f0160}
|
||||
'@hcengineering/communication-types@0.1.174':
|
||||
resolution: {integrity: sha512-rydGR+leAkU0ATPf+xMu0FdV6I78r+6mV3oD505fcfc43d59WQcb4VqiIEck9gnVfWezSoXEApenm2uKD7ruDQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-types/0.1.174/226647822d778d1e86bc9c5ac6d8b270684d4994}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/communication-yaml@0.1.172':
|
||||
resolution: {integrity: sha512-GxWiIEPH+xO1YU1b52uJxuvRrhMnzGiIyxqN7D51TCkqjKEUTl4ZqEPD4uMyiWU1iXjUF3Q8C+MecdcQXuvcjA==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-yaml/0.1.172/2e4ae4b9f3106b5493a1a79b9ff3a0bb41a9641f}
|
||||
'@hcengineering/communication-yaml@0.1.174':
|
||||
resolution: {integrity: sha512-iBCC5beUV36ETxpQjCDESU86tk/6Y/oSLvdvQVMG4Q2TtTqODqPxiPJZ8rWUGZv2JomecYE+XcY7541x411HpA==, tarball: https://npm.pkg.github.com/download/@hcengineering/communication-yaml/0.1.174/5b79a08820c011aa58f4897688c6d94d777f6a89}
|
||||
peerDependencies:
|
||||
typescript: ^5.6.3
|
||||
|
||||
'@hcengineering/core@0.6.490':
|
||||
resolution: {integrity: sha512-BnYeOeSBxjYcwAwGcXcTcmLbNo0ft2Pt7QoDlHV4KLuDCQkU0Xw6hUvDgMyz6irHKciCa0jBdZ2vOgvBTTe3ug==, tarball: https://npm.pkg.github.com/download/@hcengineering/core/0.6.490/562815e33c0dca6833a43d71745ebb12fa6e7cb9}
|
||||
|
||||
'@hcengineering/core@0.7.28':
|
||||
resolution: {integrity: sha512-qv4QE7mkect6JYlGMljW5CQ2uU80hFGq0E17lZ5rO79h1boWEKLJpINv+w3J2BdR/nNG7taIsdZg3yfl9fY4bg==, tarball: https://npm.pkg.github.com/download/@hcengineering/core/0.7.28/43b84c63262e2b8fe5554c1967812e2ce6bb56e1}
|
||||
|
||||
'@hcengineering/drive@0.6.490':
|
||||
resolution: {integrity: sha512-UCcs/SQeXSP/PinDmyh/F6qMW3Ji4CI1nQYCLsxcMei6XHwXyMqfVppeqKpbmGVV+5HJOjAsbSaJe2EiLy6l5Q==, tarball: https://npm.pkg.github.com/download/@hcengineering/drive/0.6.490/270638c5412bb3cf2ac5f2a207896b069f87adb9}
|
||||
|
||||
'@hcengineering/platform@0.6.490':
|
||||
resolution: {integrity: sha512-jtCHMznMpbPJQaX2RTbKN0tR5e2YgSrIYWHREXgi8VIAIygMLNtzkkNkVX/2FgcOHK+Gs1aF3mf4gsikiKyyKw==, tarball: https://npm.pkg.github.com/download/@hcengineering/platform/0.6.490/45e5e6cbd7fcb12cf241c5ace3c027689052f454}
|
||||
|
||||
'@hcengineering/platform@0.7.28':
|
||||
resolution: {integrity: sha512-0zEifwsLdOs/M6TZ9xnPrQTTlhwW28sooiyL4ZfQsiC2AJUy05vLP5/W8V9eDLta+EiR5bjtlulGsg1GfPjUoQ==, tarball: https://npm.pkg.github.com/download/@hcengineering/platform/0.7.28/2126ff97284b679ceab3c86f24febd73a3a28712}
|
||||
|
||||
'@hcengineering/preference@0.6.490':
|
||||
resolution: {integrity: sha512-gwX9U1T2H3A/yDoT2DLFn4SPD9Ki1mQ4bp3MhbPc6uc/cv8Dm2eD/nFM1viT2j03TrM8caKIpB0epONH3qj12g==, tarball: https://npm.pkg.github.com/download/@hcengineering/preference/0.6.490/9e1a4219a1cbec866faf43f7584abcda8fb9b6c2}
|
||||
|
||||
'@hcengineering/preference@0.7.28':
|
||||
resolution: {integrity: sha512-WwwOfjZ1TLdTfPhQGvSjo8dS63HyuE7BDVhfstxP8D+H4BI5UKYoev/6vlwQf/3d+jI1S4f2ivO//IDJAD7sGg==, tarball: https://npm.pkg.github.com/download/@hcengineering/preference/0.7.28/f1739991cc012d194fa18f99565ae5bd64f0ad07}
|
||||
|
||||
@@ -3066,15 +3060,9 @@ packages:
|
||||
'@hcengineering/tags@0.7.28':
|
||||
resolution: {integrity: sha512-2KCVUu5N/GAkDsDRbdUi7gnBq4ze1Z3eCLoc8nz2G/zeAjAga8gmWkZEbXqAC8rNVqBQv72EKeJFGJyqnev6Xw==, tarball: https://npm.pkg.github.com/download/@hcengineering/tags/0.7.28/42545cc43e3c61e32ce96be87c245fa929f5cbb6}
|
||||
|
||||
'@hcengineering/theme@0.6.490':
|
||||
resolution: {integrity: sha512-avJpw+/Sx0xZDctrFImANYBGK4TXdOphI158jcWgpC1ys6IBiRHKeeUtquTKud8q9mE06jb7TjOt9Oo/wrCGWg==, tarball: https://npm.pkg.github.com/download/@hcengineering/theme/0.6.490/2f8704cc5a089ce66e7d6dae4aa3ade6f3ea9b7a}
|
||||
|
||||
'@hcengineering/theme@0.7.28':
|
||||
resolution: {integrity: sha512-Hv3wQKHr327TC7wMHCBiG4bMtg8vSlb7+UFwdKI8ztEs3359meqkXu+exqi7Nl5334voXIz5ZFxjwZwOMzNSFA==, tarball: https://npm.pkg.github.com/download/@hcengineering/theme/0.7.28/557640a7ba2ffaa4d6e5411a54577f60dc528300}
|
||||
|
||||
'@hcengineering/ui@0.6.490':
|
||||
resolution: {integrity: sha512-W/7ljW5a/nSfzHQjJRknlnUkKC9vGRkXUjOiBKIjMiJxw7NZwNyfv5quQxNswdARMYRrAfcfdxUOhEmIZYC2Lg==, tarball: https://npm.pkg.github.com/download/@hcengineering/ui/0.6.490/27bb6fcefc46410988abe75404bbd0465d0dd2a1}
|
||||
|
||||
'@hcengineering/ui@0.7.28':
|
||||
resolution: {integrity: sha512-QsUpO0+Idu1n2dC6KtorPJ6SSp30It8FHSuG3Y+Awv4td/ftVocOSFqhskbk+us9Yw9KqOYgkqhGYEHbfRfw4Q==, tarball: https://npm.pkg.github.com/download/@hcengineering/ui/0.7.28/82025fc775702ea8c8569611356662bfbf28eb74}
|
||||
|
||||
@@ -3972,7 +3960,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/activity-resources@file:projects/activity-resources.tgz':
|
||||
resolution: {integrity: sha512-EmICsTg7F8yX7wkZzQhe5L/SCQ+3XJgq4k8VC1Mji+6RPxEhvagBeOKDtQM8Rmg5oJvvQn93unq78kduusuetg==, tarball: file:projects/activity-resources.tgz}
|
||||
resolution: {integrity: sha512-eC+r253HtclWdPx0PoLIu3zhvQRHvyT10jqAzvO4JOf4hbmNKj8eBLNkNWDnTXmNa0erH2zdPG6gzM08hVoc+g==, tarball: file:projects/activity-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/activity@file:projects/activity.tgz':
|
||||
@@ -4076,7 +4064,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/card-resources@file:projects/card-resources.tgz':
|
||||
resolution: {integrity: sha512-7714jtYqpTQ+VyWjObiRlGB3X64f9sOfwF1vqYjkJMwi1MWq7xGn294QvOzPDuEjPvOZzfDLJpUd3VVsOn0VsQ==, tarball: file:projects/card-resources.tgz}
|
||||
resolution: {integrity: sha512-DQsKJ5FhJ6nucCcWic8n9F6ut/bvGbs9+cTHIhv9PmKaKr3f9bxcQY7yjsOlvw9aJw12uOfZpMmhft4XFcK7dg==, tarball: file:projects/card-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/card@file:projects/card.tgz':
|
||||
@@ -4088,7 +4076,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/chat-resources@file:projects/chat-resources.tgz':
|
||||
resolution: {integrity: sha512-uRaHRIJND7Bkr8M16shYH8YjwyMO7ytjXrogMh3m6yv3acZGCN11sXoeoRpO2+jeUxJ+03o3gBDTFTeTWNfqCw==, tarball: file:projects/chat-resources.tgz}
|
||||
resolution: {integrity: sha512-0DNiq9IJXQbQsUkcEqaXm/8HrxJJfg1Q+vfDSxMi1wmmBvlMd9QXhhdA53mZRLJ4qa4eP/0Ruaai2+Cb6+q1Ig==, tarball: file:projects/chat-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/chat@file:projects/chat.tgz':
|
||||
@@ -4108,7 +4096,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/client-resources@file:projects/client-resources.tgz':
|
||||
resolution: {integrity: sha512-oCxf8CrpgoWEHY/wQ32dMlvGt7jEHwf2nSOkOhxuETwbOwZahA/+5MuvSe4bBQ58quLYt1FEMptJsSg3ZP1kkA==, tarball: file:projects/client-resources.tgz}
|
||||
resolution: {integrity: sha512-KoWLuivv/b8oseSErcCLwes9L3smXAVw7rzqGea7b80UnS4ntBkZD4VIwH7jX41xhNrlIiSjXAxCJf0QPY+LlQ==, tarball: file:projects/client-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/client@file:projects/client.tgz':
|
||||
@@ -4127,6 +4115,18 @@ packages:
|
||||
resolution: {integrity: sha512-t7F9Hgow7TzMVkYDQW72SgRoeSh5ZQxnvmSycWRrHcSQCtiWqQe0AT7/Sx5oZKWos3hGjUA5GIJi/toJioVmOg==, tarball: file:projects/collaborator.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/communication-assets@file:projects/communication-assets.tgz':
|
||||
resolution: {integrity: sha512-1BcpdOgbhmh+R1rqstyhhHJy0Nw0qd8HN7dlWwEiIjsWtTsQpuFXbPIdSAN71TBLbxVzR0YH+KIFRyE4eSx87g==, tarball: file:projects/communication-assets.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/communication-resources@file:projects/communication-resources.tgz':
|
||||
resolution: {integrity: sha512-LMnZ2ZHr8E8jS3M8c4LAM5KGAGnP1QAD4g1e15pEr+cFvNXzhK5laeMCNaLeJDGy0xF/+lGlRcDuu/w++AVplQ==, tarball: file:projects/communication-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/communication@file:projects/communication.tgz':
|
||||
resolution: {integrity: sha512-Ke3N4mmJ4M3drwvZDvhWMKgvYL+dWpXkIG0DEne45V62XyxJgz+RWTYUqZ5pwNQx3L6Ki6nX6qijaXrHzDXTKA==, tarball: file:projects/communication.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/contact-assets@file:projects/contact-assets.tgz':
|
||||
resolution: {integrity: sha512-PRl7vfRPda3ntMSUZkOEA7qVPSgndwY9vq4bagurqjvhdhvKfoKNRdWXmlVs1eSwAB0dJErw7/AlvU7ryQSIrA==, tarball: file:projects/contact-assets.tgz}
|
||||
version: 0.0.0
|
||||
@@ -4176,7 +4176,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/desktop@file:projects/desktop.tgz':
|
||||
resolution: {integrity: sha512-CP0b8VHDy4SDT6BEqg5fUrc6WG5AVwWslxiyDi6bkGFaLnIG8aSw4HKHj0kkMmZ8WJtZdfvmk3z5JH47A6GkoA==, tarball: file:projects/desktop.tgz}
|
||||
resolution: {integrity: sha512-2MuxT1ciufuMIFtWSoBJlO0uNhPmICCXRVnZZOQji4ByNWBvm4RSkPd97BQic8PxYe4H4FlPmIylRsvvVaeU7w==, tarball: file:projects/desktop.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/devmodel-resources@file:projects/devmodel-resources.tgz':
|
||||
@@ -4316,7 +4316,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/inbox-resources@file:projects/inbox-resources.tgz':
|
||||
resolution: {integrity: sha512-nOcoALHs+JLfTFLVFLt3swxNp0ewoxJlfyHJ8rOPYkwDvaTvI7E0G8XKgUoVojZeTX+oR/3KyWqjCrcaf8YuPA==, tarball: file:projects/inbox-resources.tgz}
|
||||
resolution: {integrity: sha512-VXtnI7lkLa7Oe94ftplqjev46LkmgK05a6YvruXnejgUolNrKjVvSgZIw4l6b3/4JzaI+MdC4P/s0qvajYz76g==, tarball: file:projects/inbox-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/inbox@file:projects/inbox.tgz':
|
||||
@@ -4428,7 +4428,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-all@file:projects/model-all.tgz':
|
||||
resolution: {integrity: sha512-SKstK5NwxlHraDMcD0qfHJru8wR+/XtOzfor1keyKWbVlzbAp65YO8lzua3kd2IP+P9MtsOf8WMMzQX2f5s+iw==, tarball: file:projects/model-all.tgz}
|
||||
resolution: {integrity: sha512-apw/K0//cfSDJtJQ6h8Y9RmfYgpBq67AAr1hxPrSg8kYLMPzhro1u/0Iuj+jJGnbv874rVprV8VWZznoDD5m8A==, tarball: file:projects/model-all.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-analytics-collector@file:projects/model-analytics-collector.tgz':
|
||||
@@ -4456,13 +4456,17 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-chat@file:projects/model-chat.tgz':
|
||||
resolution: {integrity: sha512-OuLdR05w3mKXbRksmTM4ZC5Cmm757vz4gUH08PHzDVtrOJU/gq4lkAhdqzFgEKnV8nXN4mZ7Cn3Ra/1NDAcKuQ==, tarball: file:projects/model-chat.tgz}
|
||||
resolution: {integrity: sha512-WBNBH/Nt5693IYF9/RjvGohd42lP6/Pw8E4exrWnJa14QWg4Mdy5sO2/7TGYU9/kPboldNhJjMHg9j25QjIw9Q==, tarball: file:projects/model-chat.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-chunter@file:projects/model-chunter.tgz':
|
||||
resolution: {integrity: sha512-es0oJ+MzCyOR75Kdx2An+tBhga3cZCaPV24k7V4LtlxXyxmboZjiDhZgh9/56psQwWgT7qqL6XBPzCR4nZBV1g==, tarball: file:projects/model-chunter.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-communication@file:projects/model-communication.tgz':
|
||||
resolution: {integrity: sha512-Fbi79c8xZjCCG892THwn1EHUSA5CecN/DhcyibrsjwWMJP5W4jLnv+2iJhwKHZNZ/bUnRDgKFv5iWUIPu28WDA==, tarball: file:projects/model-communication.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-contact@file:projects/model-contact.tgz':
|
||||
resolution: {integrity: sha512-R5QhJlkccqefuHjHaIg/POYsrtnWCYDPE6MwNTQ+1F/CxGYuCJ2kDfEZMlKZiLitiruAkKbvq8xBo/nl2/PNfw==, tarball: file:projects/model-contact.tgz}
|
||||
version: 0.0.0
|
||||
@@ -4564,7 +4568,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-recorder@file:projects/model-recorder.tgz':
|
||||
resolution: {integrity: sha512-zYwcCJVba+KhkMPQhgD7+ePk4S+zv9VyJ4h5PdIGgxfafKhugx5hcwVUthjVlgjyTs4merYQoTFl4ys30KatZA==, tarball: file:projects/model-recorder.tgz}
|
||||
resolution: {integrity: sha512-qFjvdP1IJmVy2FJQ4YvRu/GeQCxxvLJKT39tBv1EIwL7/DV1eENAfSw2HNkanWAUtUKHGnqnmAm348KBVRNQNw==, tarball: file:projects/model-recorder.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/model-recruit@file:projects/model-recruit.tgz':
|
||||
@@ -4864,7 +4868,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/pod-inbound-mail@file:projects/pod-inbound-mail.tgz':
|
||||
resolution: {integrity: sha512-iC+pqJO5+ZG4SVopo+kXW+ROqVyMddxjDWLWfZGztLTuygK6wjCMNVbyGhJxNAmliTOsNajzEVtmRDIaNA29GQ==, tarball: file:projects/pod-inbound-mail.tgz}
|
||||
resolution: {integrity: sha512-k2IG0e/Pk2KOW8f/S/hbKPB3Erh2Yiv9KMu/+IyOYVGMhDt/DR+usttRsCD7NOWqFtiy250y2GpaJRq/qQGqBg==, tarball: file:projects/pod-inbound-mail.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/pod-love@file:projects/pod-love.tgz':
|
||||
@@ -4876,7 +4880,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/pod-msg2file@file:projects/pod-msg2file.tgz':
|
||||
resolution: {integrity: sha512-+Wes98hofxmU3stiB7+xfmPv9zAak7Q2UAhTuC1m++A59iYjnkMwcn9Q/ywRQH+FF45qWeaMYv/AhuMyWnibqw==, tarball: file:projects/pod-msg2file.tgz}
|
||||
resolution: {integrity: sha512-umk2MHdV65UvS6rIDTcXCjmUc3KBETgY7ojUSirgcvxztmC1JdgQ8g8D4DFzX7StQa0+fAGz5og36007IYP33A==, tarball: file:projects/pod-msg2file.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/pod-print@file:projects/pod-print.tgz':
|
||||
@@ -4884,7 +4888,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/pod-server@file:projects/pod-server.tgz':
|
||||
resolution: {integrity: sha512-KQSuVq8PFZHfqzogcEEMH3EuVOQZ2AteuXD/5J1FAURYl817QB/zzqC3WtiZ6yt8rwWRTI8NwM/a2VVKTUGZ3Q==, tarball: file:projects/pod-server.tgz}
|
||||
resolution: {integrity: sha512-NP25MUnqfYgXVn14uYSuhFF/C5tZ3fyutLQIdbghWCNNfa+Cln/vUrmB7F6n7JxthgAg8XCn7HOfjWuLPYxtww==, tarball: file:projects/pod-server.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/pod-ses@file:projects/pod-ses.tgz':
|
||||
@@ -4932,7 +4936,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/presentation@file:projects/presentation.tgz':
|
||||
resolution: {integrity: sha512-nzzqiGqoRHekqhXV+0wGXdsgwa5PAiehwe+pFzuNFarYRDhS2mzaF4SwKgyAz9A3gN1dAbjLCWaA553AUNFqgQ==, tarball: file:projects/presentation.tgz}
|
||||
resolution: {integrity: sha512-GzaUoAROzVGtzTqXVF+kJt3ESvx65cESPTpWvhUKjISbwVzfCFDiNwYhYIRWgrKeVxVt6YvqYj3dupaARV/j3Q==, tarball: file:projects/presentation.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/print-assets@file:projects/print-assets.tgz':
|
||||
@@ -4960,7 +4964,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/prod@file:projects/prod.tgz':
|
||||
resolution: {integrity: sha512-D3+eukzHy1uZ6wlLr+FxaVXntbuYZU/VEmDc1+TBNT6C/1/yB0oUJBDAiJnRsKPOsjSiU1NYw0HKoimvHhdhOw==, tarball: file:projects/prod.tgz}
|
||||
resolution: {integrity: sha512-sH+/06L2vJs2pfZD+n0Lir0YqObICbAlwOUjLMmJGWoQNGn5SrK85M9asNA5w4FbzKSHMLoSarNHebM7Th8ipQ==, tarball: file:projects/prod.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/products-assets@file:projects/products-assets.tgz':
|
||||
@@ -5012,7 +5016,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/recorder@file:projects/recorder.tgz':
|
||||
resolution: {integrity: sha512-/Oi8ZzFzINaPy13dn0+UfkU+0VdCVzBOgXmArnYDqAq2ow503KqMf8Zv3/rW8oQOlYeS6Jdy6TlGp+IMX2CQuQ==, tarball: file:projects/recorder.tgz}
|
||||
resolution: {integrity: sha512-IPl6+cYfRw0rnCL5+4Eajn1zM7YTXPqzON6XGVvNDjEj2PkFJnaENne98ZYdcwYWU/X3kamnteOqx145wlrpJQ==, tarball: file:projects/recorder.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/recruit-assets@file:projects/recruit-assets.tgz':
|
||||
@@ -5060,7 +5064,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/server-activity-resources@file:projects/server-activity-resources.tgz':
|
||||
resolution: {integrity: sha512-6NGQljoDn5dLuKbCU+CAxoBdJkFhGWbsoLwrZdBisIxEr1hj1xIeeDAtaAMLRld+epgMX+0AcG5EQrLxLp/A7w==, tarball: file:projects/server-activity-resources.tgz}
|
||||
resolution: {integrity: sha512-O1HkbFlpkESkoXDZUBhWn1wcTUT8v+wsuhMARNbDw4z7FkwwzZnQW+b4dlQz81lWgWvJgNftQiNOcM6oJR6T3w==, tarball: file:projects/server-activity-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/server-activity@file:projects/server-activity.tgz':
|
||||
@@ -5104,7 +5108,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/server-card-resources@file:projects/server-card-resources.tgz':
|
||||
resolution: {integrity: sha512-700pMI2ppFiIVXIXF712BaTrsbLG2iQpWc+jd0E+CVmMLHvq51t47zqnqkrzsnprQirXka9t6XM1GXiVFTuulA==, tarball: file:projects/server-card-resources.tgz}
|
||||
resolution: {integrity: sha512-GFpXvTyz3YmI+3M/nu/YLhu1yfNvMszn/n0Hh5M7WQN8Ls8y9ReDpo5mq0O8kxuqVVDiCNmVpUZlMnu3Xgc1Sw==, tarball: file:projects/server-card-resources.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/server-card@file:projects/server-card.tgz':
|
||||
@@ -5148,7 +5152,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/server-core@file:projects/server-core.tgz':
|
||||
resolution: {integrity: sha512-87zGXHlESgiz1g5FdqHBMQQ5MgqcPhBVoS3x/baKkPSg523llWzGNqQ+BZuCg7eUmPzf2NIVaVXDssq/EQ1CHw==, tarball: file:projects/server-core.tgz}
|
||||
resolution: {integrity: sha512-HoqF5Rq95I3jae3KoyYrdSu/AuHlM7/vf0t9ZaEiW3peme0lEQ3iO/jA7eIBUaP2D5sMHwZLriYvUGagCq8U5g==, tarball: file:projects/server-core.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/server-document-resources@file:projects/server-document-resources.tgz':
|
||||
@@ -5352,7 +5356,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/server@file:projects/server.tgz':
|
||||
resolution: {integrity: sha512-Ek116xoAlCP51m2adUYtxibMRAdufFNyxfHLowdOynye2x+tusPaIbjnCUAtBwPx/H6yxH9/wGKNg0jLUE4tpg==, tarball: file:projects/server.tgz}
|
||||
resolution: {integrity: sha512-DOy7BhJo1N0KhOzdXfmTYTB53NXKztkGwYpJoVgKqqVs0I0y6cIvCt88fR3xuAJC33HwrP72aeZ/UPNhv/qakQ==, tarball: file:projects/server.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/setting-assets@file:projects/setting-assets.tgz':
|
||||
@@ -5544,7 +5548,7 @@ packages:
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/ui-next@file:projects/ui-next.tgz':
|
||||
resolution: {integrity: sha512-bisoYF6n3HWSicnaOnc1DhInOtgSsIW77QjtWRtuq3lmJMzKQ8u+RF2wqa6gUaw3Qa/qcbE+HyzkJGQyCVB0og==, tarball: file:projects/ui-next.tgz}
|
||||
resolution: {integrity: sha512-ZzaX4T3iVbJ0L+gUEe0BO+D0weMrHQ7Yyp75BTkDh1UaJIsS/6cQe+qlzkbewxbApcsXqOnCQsYVvahoFCNSzQ==, tarball: file:projects/ui-next.tgz}
|
||||
version: 0.0.0
|
||||
|
||||
'@rush-temp/ui@file:projects/ui.tgz':
|
||||
@@ -14925,10 +14929,6 @@ snapshots:
|
||||
'@hcengineering/core': 0.7.28
|
||||
'@hcengineering/platform': 0.7.28
|
||||
|
||||
'@hcengineering/analytics@0.6.490':
|
||||
dependencies:
|
||||
'@hcengineering/platform': 0.6.490
|
||||
|
||||
'@hcengineering/analytics@0.7.28':
|
||||
dependencies:
|
||||
'@hcengineering/platform': 0.7.28
|
||||
@@ -14939,155 +14939,132 @@ snapshots:
|
||||
'@hcengineering/platform': 0.7.28
|
||||
'@hcengineering/ui': 0.7.28
|
||||
|
||||
'@hcengineering/communication-client-query@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-client-query@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-query': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-query': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
fast-equals: 5.2.2
|
||||
typescript: 5.3.3
|
||||
|
||||
'@hcengineering/communication-cockroach@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-cockroach@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
postgres: 3.4.5
|
||||
typescript: 5.3.3
|
||||
uuid: 11.1.0
|
||||
|
||||
'@hcengineering/communication-query@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-query@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-yaml': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-yaml': 0.1.174(typescript@5.3.3)
|
||||
fast-equals: 5.2.2
|
||||
typescript: 5.3.3
|
||||
uuid: 11.1.0
|
||||
|
||||
'@hcengineering/communication-rest-client@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-rest-client@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/core': 0.7.28
|
||||
snappyjs: 0.7.0
|
||||
typescript: 5.3.3
|
||||
|
||||
'@hcengineering/communication-rest-client@0.1.172(typescript@5.7.3)':
|
||||
'@hcengineering/communication-rest-client@0.1.174(typescript@5.7.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-shared': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-shared': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/core': 0.7.28
|
||||
snappyjs: 0.7.0
|
||||
typescript: 5.7.3
|
||||
|
||||
'@hcengineering/communication-sdk-types@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-sdk-types@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/core': 0.7.28
|
||||
typescript: 5.3.3
|
||||
|
||||
'@hcengineering/communication-sdk-types@0.1.172(typescript@5.7.3)':
|
||||
'@hcengineering/communication-sdk-types@0.1.174(typescript@5.7.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/core': 0.7.28
|
||||
typescript: 5.7.3
|
||||
|
||||
'@hcengineering/communication-server@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-server@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/account-client': 0.7.28
|
||||
'@hcengineering/communication-cockroach': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-cockroach': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/core': 0.7.28
|
||||
'@hcengineering/platform': 0.7.28
|
||||
'@hcengineering/server-token': 0.7.28
|
||||
typescript: 5.3.3
|
||||
zod: 3.24.2
|
||||
|
||||
'@hcengineering/communication-shared@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-shared@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
typescript: 5.3.3
|
||||
|
||||
'@hcengineering/communication-shared@0.1.172(typescript@5.7.3)':
|
||||
'@hcengineering/communication-shared@0.1.174(typescript@5.7.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
typescript: 5.7.3
|
||||
|
||||
'@hcengineering/communication-types@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-types@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/card': 0.7.28
|
||||
'@hcengineering/core': 0.7.28
|
||||
'@hcengineering/tags': 0.7.28
|
||||
typescript: 5.3.3
|
||||
|
||||
'@hcengineering/communication-types@0.1.172(typescript@5.6.2)':
|
||||
'@hcengineering/communication-types@0.1.174(typescript@5.6.2)':
|
||||
dependencies:
|
||||
'@hcengineering/card': 0.7.28
|
||||
'@hcengineering/core': 0.7.28
|
||||
'@hcengineering/tags': 0.7.28
|
||||
typescript: 5.6.2
|
||||
|
||||
'@hcengineering/communication-types@0.1.172(typescript@5.7.3)':
|
||||
'@hcengineering/communication-types@0.1.174(typescript@5.7.3)':
|
||||
dependencies:
|
||||
'@hcengineering/card': 0.7.28
|
||||
'@hcengineering/core': 0.7.28
|
||||
'@hcengineering/tags': 0.7.28
|
||||
typescript: 5.7.3
|
||||
|
||||
'@hcengineering/communication-yaml@0.1.172(typescript@5.3.3)':
|
||||
'@hcengineering/communication-yaml@0.1.174(typescript@5.3.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-shared': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-shared': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
js-yaml: 4.1.0
|
||||
typescript: 5.3.3
|
||||
|
||||
'@hcengineering/communication-yaml@0.1.172(typescript@5.7.3)':
|
||||
'@hcengineering/communication-yaml@0.1.174(typescript@5.7.3)':
|
||||
dependencies:
|
||||
'@hcengineering/communication-shared': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-shared': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
js-yaml: 4.1.0
|
||||
typescript: 5.7.3
|
||||
|
||||
'@hcengineering/core@0.6.490':
|
||||
dependencies:
|
||||
'@hcengineering/analytics': 0.6.490
|
||||
'@hcengineering/platform': 0.6.490
|
||||
fast-equals: 5.2.2
|
||||
|
||||
'@hcengineering/core@0.7.28':
|
||||
dependencies:
|
||||
'@hcengineering/analytics': 0.7.28
|
||||
'@hcengineering/platform': 0.7.28
|
||||
fast-equals: 5.2.2
|
||||
|
||||
'@hcengineering/drive@0.6.490':
|
||||
dependencies:
|
||||
'@hcengineering/core': 0.6.490
|
||||
'@hcengineering/platform': 0.6.490
|
||||
'@hcengineering/preference': 0.6.490
|
||||
'@hcengineering/ui': 0.6.490
|
||||
|
||||
'@hcengineering/platform@0.6.490':
|
||||
dependencies:
|
||||
intl-messageformat: 10.7.14
|
||||
|
||||
'@hcengineering/platform@0.7.28':
|
||||
dependencies:
|
||||
intl-messageformat: 10.7.14
|
||||
|
||||
'@hcengineering/preference@0.6.490':
|
||||
dependencies:
|
||||
'@hcengineering/core': 0.6.490
|
||||
'@hcengineering/platform': 0.6.490
|
||||
'@hcengineering/ui': 0.6.490
|
||||
|
||||
'@hcengineering/preference@0.7.28':
|
||||
dependencies:
|
||||
'@hcengineering/core': 0.7.28
|
||||
@@ -15107,35 +15084,12 @@ snapshots:
|
||||
'@hcengineering/ui': 0.7.28
|
||||
'@hcengineering/view': 0.7.28
|
||||
|
||||
'@hcengineering/theme@0.6.490':
|
||||
dependencies:
|
||||
'@hcengineering/analytics': 0.6.490
|
||||
'@hcengineering/platform': 0.6.490
|
||||
svelte: 4.2.19
|
||||
|
||||
'@hcengineering/theme@0.7.28':
|
||||
dependencies:
|
||||
'@hcengineering/analytics': 0.7.28
|
||||
'@hcengineering/platform': 0.7.28
|
||||
svelte: 4.2.19
|
||||
|
||||
'@hcengineering/ui@0.6.490':
|
||||
dependencies:
|
||||
'@hcengineering/analytics': 0.6.490
|
||||
'@hcengineering/core': 0.6.490
|
||||
'@hcengineering/platform': 0.6.490
|
||||
'@hcengineering/theme': 0.6.490
|
||||
autolinker: 4.0.0
|
||||
date-fns: 2.30.0
|
||||
date-fns-tz: 2.0.0(date-fns@2.30.0)
|
||||
dompurify: 3.2.3
|
||||
emoji-regex: 10.3.0
|
||||
emojibase: 16.0.0
|
||||
fast-equals: 5.2.2
|
||||
hls.js: 1.5.20
|
||||
plyr: 3.7.8
|
||||
svelte: 4.2.19
|
||||
|
||||
'@hcengineering/ui@0.7.28':
|
||||
dependencies:
|
||||
'@hcengineering/analytics': 0.7.28
|
||||
@@ -16536,7 +16490,7 @@ snapshots:
|
||||
|
||||
'@rush-temp/activity-resources@file:projects/activity-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.3.3)
|
||||
@@ -17360,7 +17314,7 @@ snapshots:
|
||||
|
||||
'@rush-temp/card-resources@file:projects/card-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@tiptap/pm@2.11.7)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.6.2)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.6.2)
|
||||
'@tiptap/core': 2.11.7(@tiptap/pm@2.11.7)
|
||||
'@types/html-to-text': 8.1.1
|
||||
'@types/jest': 29.5.12
|
||||
@@ -17455,7 +17409,7 @@ snapshots:
|
||||
|
||||
'@rush-temp/chat-resources@file:projects/chat-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
@@ -17615,8 +17569,8 @@ snapshots:
|
||||
|
||||
'@rush-temp/client-resources@file:projects/client-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@types/snappyjs': 0.7.1
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3)
|
||||
@@ -17775,6 +17729,99 @@ snapshots:
|
||||
- y-prosemirror
|
||||
- y-protocols
|
||||
|
||||
'@rush-temp/communication-assets@file:projects/communication-assets.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@types/jest': 29.5.12
|
||||
'@types/node': 20.11.19
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
eslint: 8.56.0
|
||||
eslint-config-standard-with-typescript: 40.0.0(@typescript-eslint/eslint-plugin@6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3))(eslint-plugin-import@2.29.1(eslint@8.56.0))(eslint-plugin-n@15.7.0(eslint@8.56.0))(eslint-plugin-promise@6.1.1(eslint@8.56.0))(eslint@8.56.0)(typescript@5.7.3)
|
||||
eslint-plugin-import: 2.29.1(eslint@8.56.0)
|
||||
eslint-plugin-n: 15.7.0(eslint@8.56.0)
|
||||
eslint-plugin-promise: 6.1.1(eslint@8.56.0)
|
||||
jest: 29.7.0(@types/node@20.11.19)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
prettier: 3.2.5
|
||||
ts-jest: 29.1.2(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(jest@29.7.0(@types/node@20.11.19)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(typescript@5.7.3)
|
||||
typescript: 5.7.3
|
||||
transitivePeerDependencies:
|
||||
- '@babel/core'
|
||||
- '@jest/types'
|
||||
- babel-jest
|
||||
- babel-plugin-macros
|
||||
- esbuild
|
||||
- node-notifier
|
||||
- supports-color
|
||||
- ts-node
|
||||
|
||||
'@rush-temp/communication-resources@file:projects/communication-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@types/node': 20.11.19
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
autoprefixer: 10.4.17(postcss@8.5.3)
|
||||
eslint: 8.56.0
|
||||
eslint-config-standard-with-typescript: 40.0.0(@typescript-eslint/eslint-plugin@6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3))(eslint-plugin-import@2.29.1(eslint@8.56.0))(eslint-plugin-n@15.7.0(eslint@8.56.0))(eslint-plugin-promise@6.1.1(eslint@8.56.0))(eslint@8.56.0)(typescript@5.7.3)
|
||||
eslint-plugin-import: 2.29.1(eslint@8.56.0)
|
||||
eslint-plugin-n: 15.7.0(eslint@8.56.0)
|
||||
eslint-plugin-promise: 6.1.1(eslint@8.56.0)
|
||||
eslint-plugin-svelte: 2.35.1(eslint@8.56.0)(svelte@4.2.19)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
jest: 29.7.0(@types/node@20.11.19)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
postcss: 8.5.3
|
||||
prettier: 3.2.5
|
||||
prettier-plugin-svelte: 3.2.2(prettier@3.2.5)(svelte@4.2.19)
|
||||
sass: 1.71.1
|
||||
svelte: 4.2.19
|
||||
svelte-check: 3.6.9(@babel/core@7.23.9)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(sass@1.71.1)(svelte@4.2.19)
|
||||
svelte-eslint-parser: 0.33.1(svelte@4.2.19)
|
||||
svelte-loader: 3.2.0(svelte@4.2.19)
|
||||
svelte-preprocess: 5.1.3(@babel/core@7.23.9)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(sass@1.71.1)(svelte@4.2.19)(typescript@5.7.3)
|
||||
tailwindcss: 3.4.17(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
ts-jest: 29.1.2(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(jest@29.7.0(@types/node@20.11.19)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(typescript@5.7.3)
|
||||
typescript: 5.7.3
|
||||
transitivePeerDependencies:
|
||||
- '@babel/core'
|
||||
- '@jest/types'
|
||||
- babel-jest
|
||||
- babel-plugin-macros
|
||||
- coffeescript
|
||||
- esbuild
|
||||
- less
|
||||
- node-notifier
|
||||
- postcss-load-config
|
||||
- pug
|
||||
- stylus
|
||||
- sugarss
|
||||
- supports-color
|
||||
- ts-node
|
||||
|
||||
'@rush-temp/communication@file:projects/communication.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@types/jest': 29.5.12
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
eslint: 8.56.0
|
||||
eslint-config-standard-with-typescript: 40.0.0(@typescript-eslint/eslint-plugin@6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3))(eslint-plugin-import@2.29.1(eslint@8.56.0))(eslint-plugin-n@15.7.0(eslint@8.56.0))(eslint-plugin-promise@6.1.1(eslint@8.56.0))(eslint@8.56.0)(typescript@5.7.3)
|
||||
eslint-plugin-import: 2.29.1(eslint@8.56.0)
|
||||
eslint-plugin-n: 15.7.0(eslint@8.56.0)
|
||||
eslint-plugin-promise: 6.1.1(eslint@8.56.0)
|
||||
jest: 29.7.0(@types/node@20.11.19)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))
|
||||
prettier: 3.2.5
|
||||
ts-jest: 29.1.2(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(jest@29.7.0(@types/node@20.11.19)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(typescript@5.7.3)
|
||||
typescript: 5.7.3
|
||||
transitivePeerDependencies:
|
||||
- '@babel/core'
|
||||
- '@jest/types'
|
||||
- '@types/node'
|
||||
- babel-jest
|
||||
- babel-plugin-macros
|
||||
- esbuild
|
||||
- node-notifier
|
||||
- supports-color
|
||||
- ts-node
|
||||
|
||||
'@rush-temp/contact-assets@file:projects/contact-assets.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@types/jest': 29.5.12
|
||||
@@ -19282,7 +19329,7 @@ snapshots:
|
||||
|
||||
'@rush-temp/inbox-resources@file:projects/inbox-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
@@ -20225,6 +20272,20 @@ snapshots:
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
'@rush-temp/model-communication@file:projects/model-communication.tgz':
|
||||
dependencies:
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
eslint: 8.56.0
|
||||
eslint-config-standard-with-typescript: 40.0.0(@typescript-eslint/eslint-plugin@6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3))(eslint-plugin-import@2.29.1(eslint@8.56.0))(eslint-plugin-n@15.7.0(eslint@8.56.0))(eslint-plugin-promise@6.1.1(eslint@8.56.0))(eslint@8.56.0)(typescript@5.7.3)
|
||||
eslint-plugin-import: 2.29.1(eslint@8.56.0)
|
||||
eslint-plugin-n: 15.7.0(eslint@8.56.0)
|
||||
eslint-plugin-promise: 6.1.1(eslint@8.56.0)
|
||||
prettier: 3.2.5
|
||||
typescript: 5.7.3
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
'@rush-temp/model-contact@file:projects/model-contact.tgz(encoding@0.1.13)':
|
||||
dependencies:
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3)
|
||||
@@ -22270,8 +22331,8 @@ snapshots:
|
||||
|
||||
'@rush-temp/pod-inbound-mail@file:projects/pod-inbound-mail.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-rest-client': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-rest-client': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@tsconfig/node16': 1.0.4
|
||||
'@types/cors': 2.8.17
|
||||
'@types/express': 4.17.21
|
||||
@@ -22395,11 +22456,11 @@ snapshots:
|
||||
|
||||
'@rush-temp/pod-msg2file@file:projects/pod-msg2file.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-rest-client': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-shared': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-yaml': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-rest-client': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-shared': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@hcengineering/communication-yaml': 0.1.174(typescript@5.7.3)
|
||||
'@tsconfig/node16': 1.0.4
|
||||
'@types/cors': 2.8.17
|
||||
'@types/express': 4.17.21
|
||||
@@ -22481,7 +22542,7 @@ snapshots:
|
||||
|
||||
'@rush-temp/pod-server@file:projects/pod-server.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-server': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-server': 0.1.174(typescript@5.3.3)
|
||||
'@types/body-parser': 1.19.5
|
||||
'@types/cors': 2.8.17
|
||||
'@types/express': 4.17.21
|
||||
@@ -22934,9 +22995,9 @@ snapshots:
|
||||
|
||||
'@rush-temp/presentation@file:projects/presentation.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-client-query': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-client-query': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@types/png-chunks-extract': 1.0.2
|
||||
'@types/uuid': 8.3.4
|
||||
@@ -23590,7 +23651,6 @@ snapshots:
|
||||
|
||||
'@rush-temp/recorder@file:projects/recorder.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/drive': 0.6.490
|
||||
'@types/jest': 29.5.12
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
@@ -23943,8 +24003,8 @@ snapshots:
|
||||
|
||||
'@rush-temp/server-activity-resources@file:projects/server-activity-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.3.3)
|
||||
@@ -24223,7 +24283,7 @@ snapshots:
|
||||
|
||||
'@rush-temp/server-card-resources@file:projects/server-card-resources.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.7.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.7.3)
|
||||
'@typescript-eslint/parser': 6.21.0(eslint@8.56.0)(typescript@5.7.3)
|
||||
@@ -24506,8 +24566,8 @@ snapshots:
|
||||
|
||||
'@rush-temp/server-core@file:projects/server-core.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@types/node': 20.11.19
|
||||
'@types/uuid': 8.3.4
|
||||
@@ -25811,8 +25871,8 @@ snapshots:
|
||||
|
||||
'@rush-temp/server@file:projects/server.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-sdk-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.3.3)
|
||||
'@hcengineering/communication-sdk-types': 0.1.174(typescript@5.3.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.3.3)
|
||||
'@types/jest': 29.5.12
|
||||
'@types/node': 20.11.19
|
||||
'@typescript-eslint/eslint-plugin': 6.21.0(@typescript-eslint/parser@6.21.0(eslint@8.56.0)(typescript@5.3.3))(eslint@8.56.0)(typescript@5.3.3)
|
||||
@@ -27353,7 +27413,7 @@ snapshots:
|
||||
|
||||
'@rush-temp/ui-next@file:projects/ui-next.tgz(@babel/core@7.23.9)(@jest/types@29.6.3)(@types/node@20.11.19)(babel-jest@29.7.0(@babel/core@7.23.9))(esbuild@0.24.2)(postcss-load-config@4.0.2(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3)))(postcss@8.5.3)(ts-node@10.9.2(@types/node@20.11.19)(typescript@5.3.3))':
|
||||
dependencies:
|
||||
'@hcengineering/communication-types': 0.1.172(typescript@5.7.3)
|
||||
'@hcengineering/communication-types': 0.1.174(typescript@5.7.3)
|
||||
'@tiptap/core': 2.11.7(@tiptap/pm@2.11.7)
|
||||
'@tiptap/pm': 2.11.7
|
||||
'@types/dompurify': 3.0.5
|
||||
|
||||
@@ -240,6 +240,9 @@
|
||||
"@hcengineering/achievement": "^0.6.0",
|
||||
"@hcengineering/achievement-assets": "^0.6.0",
|
||||
"@hcengineering/achievement-resources": "^0.6.0",
|
||||
"@hcengineering/communication": "^0.6.0",
|
||||
"@hcengineering/communication-assets": "^0.6.0",
|
||||
"@hcengineering/communication-resources": "^0.6.0",
|
||||
"electron-squirrel-startup": "~1.0.0",
|
||||
"dotenv": "~16.0.0",
|
||||
"electron-context-menu": "^4.0.4",
|
||||
|
||||
@@ -66,6 +66,7 @@ import { mailId } from '@hcengineering/mail'
|
||||
import { chatId } from '@hcengineering/chat'
|
||||
import { inboxId } from '@hcengineering/inbox'
|
||||
import { achievementId } from '@hcengineering/achievement'
|
||||
import {communicationId} from '@hcengineering/communication'
|
||||
|
||||
import '@hcengineering/activity-assets'
|
||||
import '@hcengineering/analytics-collector-assets'
|
||||
@@ -117,6 +118,7 @@ import '@hcengineering/chat-assets'
|
||||
import '@hcengineering/inbox-assets'
|
||||
import '@hcengineering/achievement-assets'
|
||||
import '@hcengineering/media-assets'
|
||||
import '@hcengineering/communication-assets'
|
||||
|
||||
import analyticsCollector, { analyticsCollectorId } from '@hcengineering/analytics-collector'
|
||||
import { coreId } from '@hcengineering/core'
|
||||
@@ -230,6 +232,7 @@ function configureI18n (): void {
|
||||
addStringsLoader(inboxId, async (lang: string) => await import(`@hcengineering/inbox-assets/lang/${lang}.json`))
|
||||
addStringsLoader(processId, async (lang: string) => await import(`@hcengineering/process-assets/lang/${lang}.json`))
|
||||
addStringsLoader(achievementId, async (lang: string) => await import(`@hcengineering/achievement-assets/lang/${lang}.json`))
|
||||
addStringsLoader(communicationId, async (lang: string) => await import(`@hcengineering/communication-assets/lang/${lang}.json`))
|
||||
}
|
||||
|
||||
export async function configurePlatform (): Promise<void> {
|
||||
@@ -370,6 +373,7 @@ export async function configurePlatform (): Promise<void> {
|
||||
addLocation(mailId, () => import(/* webpackChunkName: "card" */ '@hcengineering/mail-resources'))
|
||||
addLocation(processId, () => import(/* webpackChunkName: "process" */ '@hcengineering/process-resources'))
|
||||
addLocation(achievementId, () => import(/* webpackChunkName: "achievement" */ '@hcengineering/achievement-resources'))
|
||||
addLocation(communicationId, () => import(/* webpackChunkName: "communication" */ '@hcengineering/communication-resources'))
|
||||
|
||||
setMetadata(client.metadata.FilterModel, 'ui')
|
||||
setMetadata(client.metadata.ExtraPlugins, ['preference' as Plugin])
|
||||
|
||||
@@ -271,6 +271,9 @@
|
||||
"@hcengineering/process": "^0.6.0",
|
||||
"@hcengineering/process-assets": "^0.6.0",
|
||||
"@hcengineering/process-resources": "^0.6.0",
|
||||
"@hcengineering/communication": "^0.6.0",
|
||||
"@hcengineering/communication-assets": "^0.6.0",
|
||||
"@hcengineering/communication-resources": "^0.6.0",
|
||||
"@sentry/svelte": "^8.52.1",
|
||||
"posthog-js": "~1.122.0",
|
||||
"readable-stream": "^4.7.0",
|
||||
|
||||
@@ -75,6 +75,7 @@ import github, { githubId } from '@hcengineering/github'
|
||||
import { bitrixId } from '@hcengineering/bitrix'
|
||||
import {inboxId} from '@hcengineering/inbox'
|
||||
import {achievementId} from '@hcengineering/achievement'
|
||||
import {communicationId} from '@hcengineering/communication'
|
||||
|
||||
import '@hcengineering/activity-assets'
|
||||
import '@hcengineering/analytics-collector-assets'
|
||||
@@ -128,6 +129,7 @@ import '@hcengineering/inbox-assets'
|
||||
import '@hcengineering/mail-assets'
|
||||
import '@hcengineering/github-assets'
|
||||
import '@hcengineering/achievement-assets'
|
||||
import '@hcengineering/communication-assets'
|
||||
|
||||
import { coreId } from '@hcengineering/core'
|
||||
import presentation, {
|
||||
@@ -362,6 +364,7 @@ function configureI18n(): void {
|
||||
addStringsLoader(processId, async (lang: string) => await import(`@hcengineering/process-assets/lang/${lang}.json`))
|
||||
addStringsLoader(inboxId, async (lang: string) => await import(`@hcengineering/inbox-assets/lang/${lang}.json`))
|
||||
addStringsLoader(achievementId, async (lang: string) => await import(`@hcengineering/achievement-assets/lang/${lang}.json`))
|
||||
addStringsLoader(communicationId, async (lang: string) => await import(`@hcengineering/communication-assets/lang/${lang}.json`))
|
||||
}
|
||||
|
||||
export async function configurePlatform() {
|
||||
@@ -564,6 +567,7 @@ export async function configurePlatform() {
|
||||
addLocation(processId, () => import(/* webpackChunkName: "process" */ '@hcengineering/process-resources'))
|
||||
addLocation(inboxId, () => import(/* webpackChunkName: "inbox" */ '@hcengineering/inbox-resources'))
|
||||
addLocation(achievementId, () => import(/* webpackChunkName: "achievement" */ '@hcengineering/achievement-resources'))
|
||||
addLocation(communicationId, () => import(/* webpackChunkName: "communication" */ '@hcengineering/communication-resources'))
|
||||
|
||||
setMetadata(client.metadata.FilterModel, 'ui')
|
||||
setMetadata(client.metadata.ExtraPlugins, ['preference' as Plugin])
|
||||
|
||||
@@ -123,6 +123,7 @@
|
||||
"@hcengineering/model-process": "^0.6.0",
|
||||
"@hcengineering/model-server-process": "^0.6.0",
|
||||
"@hcengineering/model-inbox": "^0.6.0",
|
||||
"@hcengineering/model-achievement": "^0.6.0"
|
||||
"@hcengineering/model-achievement": "^0.6.0",
|
||||
"@hcengineering/model-communication": "^0.6.0"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -117,6 +117,7 @@ import { chatId, createModel as chatModel } from '@hcengineering/model-chat'
|
||||
import processes, { processId, createModel as processModel } from '@hcengineering/model-process'
|
||||
import { createModel as inboxModel, inboxId } from '@hcengineering/model-inbox'
|
||||
import { achievementId, createModel as achievementModel } from '@hcengineering/model-achievement'
|
||||
import { communicationId, createModel as communicationModel } from '@hcengineering/model-communication'
|
||||
import { type Plugin } from '@hcengineering/platform'
|
||||
|
||||
interface ConfigurablePlugin extends Omit<Data<PluginConfiguration>, 'pluginId' | 'transactions'> {}
|
||||
@@ -458,6 +459,7 @@ export default function buildModel (): Builder {
|
||||
[chatModel, chatId],
|
||||
[inboxModel, inboxId],
|
||||
[achievementModel, achievementId],
|
||||
[communicationModel, communicationId],
|
||||
|
||||
[serverCoreModel, serverCoreId],
|
||||
[serverAttachmentModel, serverAttachmentId],
|
||||
|
||||
@@ -59,6 +59,7 @@ import { aiBotId, aiBotOperation } from '@hcengineering/model-ai-bot'
|
||||
import { chatId, chatOperation } from '@hcengineering/model-chat'
|
||||
import { inboxId, inboxOperation } from '@hcengineering/model-inbox'
|
||||
import { processId, processOperation } from '@hcengineering/model-process'
|
||||
import { communicationId, communicationOperation } from '@hcengineering/model-communication'
|
||||
import { recorderId, recorderOperation } from '@hcengineering/model-recorder'
|
||||
|
||||
export const migrateOperations: [string, MigrateOperation][] = [
|
||||
@@ -108,5 +109,6 @@ export const migrateOperations: [string, MigrateOperation][] = [
|
||||
[chatId, chatOperation],
|
||||
[inboxId, inboxOperation],
|
||||
[processId, processOperation],
|
||||
[communicationId, communicationOperation],
|
||||
[recorderId, recorderOperation]
|
||||
]
|
||||
|
||||
+118
-7
@@ -20,7 +20,10 @@ import {
|
||||
type MasterTag,
|
||||
type ParentInfo,
|
||||
type Tag,
|
||||
type Role
|
||||
type Role,
|
||||
type CardSection,
|
||||
type CardViewDefaults,
|
||||
type CardNavigation
|
||||
} from '@hcengineering/card'
|
||||
import chunter from '@hcengineering/chunter'
|
||||
import core, {
|
||||
@@ -34,7 +37,8 @@ import core, {
|
||||
type CollectionSize,
|
||||
type MarkupBlobRef,
|
||||
type Rank,
|
||||
type Ref
|
||||
type Ref,
|
||||
type MixinData
|
||||
} from '@hcengineering/core'
|
||||
import {
|
||||
Collection,
|
||||
@@ -45,14 +49,15 @@ import {
|
||||
TypeRef,
|
||||
TypeString,
|
||||
UX,
|
||||
type Builder
|
||||
type Builder,
|
||||
Mixin
|
||||
} from '@hcengineering/model'
|
||||
import attachment from '@hcengineering/model-attachment'
|
||||
import { TAttachedDoc, TClass, TDoc, TMixin, TSpace } from '@hcengineering/model-core'
|
||||
import presentation from '@hcengineering/model-presentation'
|
||||
import setting from '@hcengineering/model-setting'
|
||||
import view, { createAction } from '@hcengineering/model-view'
|
||||
import workbench from '@hcengineering/model-workbench'
|
||||
import workbench, { WidgetType } from '@hcengineering/model-workbench'
|
||||
import { type Asset, getEmbeddedLabel, type IntlString } from '@hcengineering/platform'
|
||||
import time, { type ToDo } from '@hcengineering/time'
|
||||
import { type AnyComponent } from '@hcengineering/ui/src/types'
|
||||
@@ -116,6 +121,20 @@ export class MasterTagEditorSection extends TDoc implements MasterTagEditorSecti
|
||||
component!: AnyComponent
|
||||
}
|
||||
|
||||
@Model(card.class.CardSection, core.class.Doc, DOMAIN_MODEL)
|
||||
export class TCardSection extends TDoc implements CardSection {
|
||||
label!: IntlString
|
||||
component!: AnyComponent
|
||||
order!: number
|
||||
navigation!: CardNavigation[]
|
||||
}
|
||||
|
||||
@Mixin(card.mixin.CardViewDefaults, card.class.MasterTag)
|
||||
export class TCardViewDefaults extends TMasterTag implements CardViewDefaults {
|
||||
defaultSection!: Ref<CardSection>
|
||||
defaultNavigation?: string
|
||||
}
|
||||
|
||||
@Model(card.class.Role, core.class.AttachedDoc, DOMAIN_MODEL)
|
||||
export class TRole extends TAttachedDoc implements Role {
|
||||
name!: string
|
||||
@@ -154,7 +173,8 @@ export function createSystemType (
|
||||
type: Ref<MasterTag>,
|
||||
icon: Asset = card.icon.MasterTag,
|
||||
label: IntlString,
|
||||
pluralLabel?: IntlString
|
||||
pluralLabel?: IntlString,
|
||||
viewDefaults?: MixinData<MasterTag, CardViewDefaults>
|
||||
): void {
|
||||
builder.createDoc(
|
||||
card.class.MasterTag,
|
||||
@@ -209,13 +229,30 @@ export function createSystemType (
|
||||
},
|
||||
config: listConfig
|
||||
})
|
||||
|
||||
if (viewDefaults !== undefined) {
|
||||
builder.mixin(type, card.class.MasterTag, card.mixin.CardViewDefaults, viewDefaults)
|
||||
}
|
||||
}
|
||||
|
||||
export function createModel (builder: Builder): void {
|
||||
builder.createModel(TMasterTag, TTag, TCard, MasterTagEditorSection, TCardSpace, TRole)
|
||||
builder.createModel(
|
||||
TMasterTag,
|
||||
TTag,
|
||||
TCard,
|
||||
MasterTagEditorSection,
|
||||
TCardSpace,
|
||||
TRole,
|
||||
TCardSection,
|
||||
TCardViewDefaults
|
||||
)
|
||||
|
||||
defineTabs(builder)
|
||||
|
||||
createSystemType(builder, card.types.File, card.icon.File, attachment.string.File, attachment.string.Files)
|
||||
createSystemType(builder, card.types.Document, card.icon.Document, card.string.Document, card.string.Documents)
|
||||
createSystemType(builder, card.types.Document, card.icon.Document, card.string.Document, card.string.Documents, {
|
||||
defaultSection: card.section.Content
|
||||
})
|
||||
|
||||
builder.createDoc(view.class.Viewlet, core.space.Model, {
|
||||
attachTo: card.class.CardSpace,
|
||||
@@ -700,6 +737,80 @@ export function createModel (builder: Builder): void {
|
||||
label: card.string.Views,
|
||||
component: card.component.ViewsSection
|
||||
})
|
||||
|
||||
builder.createDoc(
|
||||
workbench.class.Widget,
|
||||
core.space.Model,
|
||||
{
|
||||
label: card.string.Cards,
|
||||
type: WidgetType.Flexible,
|
||||
icon: card.icon.Card,
|
||||
component: card.component.CardWidget
|
||||
},
|
||||
card.ids.CardWidget
|
||||
)
|
||||
}
|
||||
|
||||
function defineTabs (builder: Builder): void {
|
||||
builder.createDoc(
|
||||
card.class.CardSection,
|
||||
core.space.Model,
|
||||
{
|
||||
label: card.string.Properties,
|
||||
component: card.sectionComponent.PropertiesSection,
|
||||
order: 100,
|
||||
navigation: []
|
||||
},
|
||||
card.section.Properties
|
||||
)
|
||||
|
||||
builder.createDoc(
|
||||
card.class.CardSection,
|
||||
core.space.Model,
|
||||
{
|
||||
label: card.string.Content,
|
||||
component: card.sectionComponent.ContentSection,
|
||||
order: 200,
|
||||
navigation: []
|
||||
},
|
||||
card.section.Content
|
||||
)
|
||||
|
||||
builder.createDoc(
|
||||
card.class.CardSection,
|
||||
core.space.Model,
|
||||
{
|
||||
label: card.string.Children,
|
||||
component: card.sectionComponent.ChildrenSection,
|
||||
order: 300,
|
||||
navigation: []
|
||||
},
|
||||
card.section.Children
|
||||
)
|
||||
|
||||
builder.createDoc(
|
||||
card.class.CardSection,
|
||||
core.space.Model,
|
||||
{
|
||||
label: attachment.string.Attachments,
|
||||
component: card.sectionComponent.AttachmentsSection,
|
||||
order: 400,
|
||||
navigation: []
|
||||
},
|
||||
card.section.Attachments
|
||||
)
|
||||
|
||||
builder.createDoc(
|
||||
card.class.CardSection,
|
||||
core.space.Model,
|
||||
{
|
||||
label: core.string.Relations,
|
||||
component: card.sectionComponent.RelationsSection,
|
||||
order: 500,
|
||||
navigation: []
|
||||
},
|
||||
card.section.Relations
|
||||
)
|
||||
}
|
||||
|
||||
export default card
|
||||
|
||||
@@ -29,6 +29,7 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@hcengineering/card": "^0.6.0",
|
||||
"@hcengineering/communication": "^0.6.0",
|
||||
"@hcengineering/chat": "^0.6.0",
|
||||
"@hcengineering/chat-resources": "^0.6.0",
|
||||
"@hcengineering/core": "^0.6.32",
|
||||
|
||||
+13
-16
@@ -18,8 +18,8 @@ import { type Builder } from '@hcengineering/model'
|
||||
import core from '@hcengineering/model-core'
|
||||
import workbench from '@hcengineering/model-workbench'
|
||||
import { chatId } from '@hcengineering/chat'
|
||||
import { WidgetType } from '@hcengineering/workbench'
|
||||
import { createSystemType } from '@hcengineering/model-card'
|
||||
import communication, { MessagesNavigationAnchors } from '@hcengineering/communication'
|
||||
|
||||
import chat from './plugin'
|
||||
|
||||
@@ -37,23 +37,20 @@ export function createModel (builder: Builder): void {
|
||||
alias: chatId,
|
||||
accessLevel: AccountRole.User,
|
||||
hidden: true,
|
||||
component: chat.component.ChatApplication
|
||||
component: chat.component.ChatApplication,
|
||||
locationResolver: chat.resolver.Location,
|
||||
locationDataResolver: chat.resolver.LocationData
|
||||
},
|
||||
chat.app.Chat
|
||||
)
|
||||
|
||||
builder.createDoc(
|
||||
workbench.class.Widget,
|
||||
core.space.Model,
|
||||
{
|
||||
label: chat.string.Chat,
|
||||
type: WidgetType.Flexible,
|
||||
icon: chat.icon.ChatBubble,
|
||||
component: chat.component.ChatWidget
|
||||
},
|
||||
chat.ids.ChatWidget
|
||||
)
|
||||
|
||||
createSystemType(builder, chat.masterTag.Thread, chat.icon.Thread, chat.string.Thread, chat.string.Threads)
|
||||
createSystemType(builder, chat.masterTag.Channel, chat.icon.Channel, chat.string.Channel, chat.string.Channels)
|
||||
// TODO: move types to communication-plugin
|
||||
createSystemType(builder, chat.masterTag.Thread, chat.icon.Thread, chat.string.Thread, chat.string.Threads, {
|
||||
defaultSection: communication.ids.CardMessagesSection,
|
||||
defaultNavigation: MessagesNavigationAnchors.LatestMessages
|
||||
})
|
||||
createSystemType(builder, chat.masterTag.Channel, chat.icon.Channel, chat.string.Channel, chat.string.Channels, {
|
||||
defaultSection: communication.ids.CardMessagesSection,
|
||||
defaultNavigation: MessagesNavigationAnchors.LatestMessages
|
||||
})
|
||||
}
|
||||
|
||||
@@ -17,10 +17,16 @@ import { chatId } from '@hcengineering/chat'
|
||||
import chat from '@hcengineering/chat-resources/src/plugin'
|
||||
import { type Ref } from '@hcengineering/core'
|
||||
import { type Application } from '@hcengineering/model-workbench'
|
||||
import { mergeIds } from '@hcengineering/platform'
|
||||
import { mergeIds, type Resource } from '@hcengineering/platform'
|
||||
import type { Location, ResolvedLocation } from '@hcengineering/ui'
|
||||
import type { LocationData } from '@hcengineering/workbench'
|
||||
|
||||
export default mergeIds(chatId, chat, {
|
||||
app: {
|
||||
Chat: '' as Ref<Application>
|
||||
},
|
||||
resolver: {
|
||||
Location: '' as Resource<(loc: Location) => Promise<ResolvedLocation | undefined>>,
|
||||
LocationData: '' as Resource<(loc: Location) => Promise<LocationData>>
|
||||
}
|
||||
})
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
module.exports = {
|
||||
extends: ['./node_modules/@hcengineering/platform-rig/profiles/model/eslint.config.json'],
|
||||
parserOptions: {
|
||||
tsconfigRootDir: __dirname,
|
||||
project: './tsconfig.json'
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,4 @@
|
||||
*
|
||||
!/lib/**
|
||||
!CHANGELOG.md
|
||||
/lib/**/__tests__/
|
||||
@@ -0,0 +1,5 @@
|
||||
{
|
||||
"$schema": "https://developer.microsoft.com/json-schemas/rig-package/rig.schema.json",
|
||||
"rigPackageName": "@hcengineering/platform-rig",
|
||||
"rigProfile": "model"
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
{
|
||||
"name": "@hcengineering/model-communication",
|
||||
"version": "0.6.0",
|
||||
"main": "lib/index.js",
|
||||
"svelte": "src/index.ts",
|
||||
"types": "types/index.d.ts",
|
||||
"author": "Copyright © Hardcore Engineering Inc.",
|
||||
"template": "@hcengineering/model-package",
|
||||
"license": "EPL-2.0",
|
||||
"scripts": {
|
||||
"build": "compile",
|
||||
"build:watch": "compile",
|
||||
"format": "format src",
|
||||
"_phase:build": "compile transpile src",
|
||||
"_phase:format": "format src",
|
||||
"_phase:validate": "compile validate"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@hcengineering/platform-rig": "^0.6.0",
|
||||
"@typescript-eslint/eslint-plugin": "^6.11.0",
|
||||
"eslint-plugin-import": "^2.26.0",
|
||||
"eslint-plugin-promise": "^6.1.1",
|
||||
"eslint-plugin-n": "^15.4.0",
|
||||
"eslint": "^8.54.0",
|
||||
"@typescript-eslint/parser": "^6.11.0",
|
||||
"eslint-config-standard-with-typescript": "^40.0.0",
|
||||
"prettier": "^3.1.0",
|
||||
"typescript": "^5.3.3"
|
||||
},
|
||||
"dependencies": {
|
||||
"@hcengineering/contact": "^0.6.24",
|
||||
"@hcengineering/core": "^0.6.32",
|
||||
"@hcengineering/model": "^0.6.11",
|
||||
"@hcengineering/model-core": "^0.6.0",
|
||||
"@hcengineering/platform": "^0.6.11",
|
||||
"@hcengineering/card": "^0.6.0",
|
||||
"@hcengineering/communication": "^0.6.0",
|
||||
"@hcengineering/communication-resources": "^0.6.0",
|
||||
"@hcengineering/ui": "^0.6.15"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
// Copyright © 2025 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 Builder } from '@hcengineering/model'
|
||||
import core from '@hcengineering/core'
|
||||
import card from '@hcengineering/card'
|
||||
import { MessagesNavigationAnchors } from '@hcengineering/communication'
|
||||
|
||||
import communication from './plugin'
|
||||
|
||||
export { communicationId } from '@hcengineering/communication'
|
||||
export * from './migration'
|
||||
|
||||
export function createModel (builder: Builder): void {
|
||||
builder.createDoc(
|
||||
card.class.CardSection,
|
||||
core.space.Model,
|
||||
{
|
||||
label: communication.string.Messages,
|
||||
component: communication.component.CardMessagesSection,
|
||||
order: 9999,
|
||||
navigation: [
|
||||
{
|
||||
id: MessagesNavigationAnchors.ConversationStart,
|
||||
label: communication.string.FirstMessages
|
||||
},
|
||||
{
|
||||
id: MessagesNavigationAnchors.LatestMessages,
|
||||
label: communication.string.LatestMessages
|
||||
}
|
||||
]
|
||||
},
|
||||
communication.ids.CardMessagesSection
|
||||
)
|
||||
}
|
||||
|
||||
export default communication
|
||||
@@ -13,11 +13,9 @@
|
||||
// limitations under the License.
|
||||
//
|
||||
|
||||
import { type Message } from '@hcengineering/communication-types'
|
||||
import { type Card } from '@hcengineering/card'
|
||||
import { type MigrateOperation } from '@hcengineering/model'
|
||||
|
||||
import { openThreadInSidebar } from './location'
|
||||
|
||||
export async function replyToThread (message: Message, parent: Card): Promise<void> {
|
||||
await openThreadInSidebar(message, parent)
|
||||
export const communicationOperation: MigrateOperation = {
|
||||
async migrate (): Promise<void> {},
|
||||
async upgrade (): Promise<void> {}
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
//
|
||||
// Copyright © 2025 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 { communicationId } from '@hcengineering/communication'
|
||||
import communication from '@hcengineering/communication-resources/src/plugin'
|
||||
import {} from '@hcengineering/core'
|
||||
import {} from '@hcengineering/ui'
|
||||
import { mergeIds } from '@hcengineering/platform'
|
||||
|
||||
export default mergeIds(communicationId, communication, {})
|
||||
@@ -0,0 +1,10 @@
|
||||
{
|
||||
"extends": "./node_modules/@hcengineering/platform-rig/profiles/model/tsconfig.json",
|
||||
|
||||
"compilerOptions": {
|
||||
"rootDir": "./src",
|
||||
"outDir": "./lib",
|
||||
"declarationDir": "./types",
|
||||
"tsBuildInfoFile": ".build/build.tsbuildinfo"
|
||||
}
|
||||
}
|
||||
@@ -63,7 +63,6 @@
|
||||
export let hideActions: boolean = false
|
||||
export let hideExtra: boolean = false
|
||||
export let overflowExtra: boolean = false
|
||||
export let newActivity: boolean = false
|
||||
|
||||
const account = getCurrentAccount()
|
||||
$: isGuest = account.role === AccountRole.DocGuest
|
||||
@@ -304,7 +303,7 @@
|
||||
{#if showActivity}
|
||||
{#key object._id}
|
||||
<Component
|
||||
is={newActivity ? activity.component.NewActivity : activity.component.Activity}
|
||||
is={activity.component.Activity}
|
||||
bind:innerRef={activityRef}
|
||||
props={{
|
||||
object,
|
||||
|
||||
@@ -43,9 +43,9 @@
|
||||
"@hcengineering/analytics": "^0.6.0",
|
||||
"@hcengineering/client": "^0.6.18",
|
||||
"@hcengineering/collaborator-client": "^0.6.4",
|
||||
"@hcengineering/communication-client-query": "0.1.172",
|
||||
"@hcengineering/communication-sdk-types": "0.1.172",
|
||||
"@hcengineering/communication-types": "0.1.172",
|
||||
"@hcengineering/communication-client-query": "0.1.174",
|
||||
"@hcengineering/communication-sdk-types": "0.1.174",
|
||||
"@hcengineering/communication-types": "0.1.174",
|
||||
"@hcengineering/core": "^0.6.32",
|
||||
"@hcengineering/diffview": "^0.6.0",
|
||||
"@hcengineering/notification": "^0.6.23",
|
||||
|
||||
@@ -28,6 +28,8 @@
|
||||
"Yesterday": "Yesterday",
|
||||
"YesterdayAt": "Yesterday at {time}",
|
||||
"AndMore": "and {count} more",
|
||||
"IsTyping": "{count, plural, =1 {is typing} other {are typing}}..."
|
||||
"IsTyping": "{count, plural, =1 {is typing} other {are typing}}...",
|
||||
"Loading": "Loading...",
|
||||
"MessageIn": "Message #{title}"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
"@hcengineering/analytics": "^0.6.0",
|
||||
"@hcengineering/attachment-resources": "^0.6.0",
|
||||
"@hcengineering/card": "^0.6.0",
|
||||
"@hcengineering/communication-types": "0.1.172",
|
||||
"@hcengineering/communication-types": "0.1.174",
|
||||
"@hcengineering/contact": "^0.6.24",
|
||||
"@hcengineering/contact-resources": "^0.6.0",
|
||||
"@hcengineering/core": "^0.6.32",
|
||||
|
||||
@@ -57,8 +57,8 @@
|
||||
.date-separator {
|
||||
display: flex;
|
||||
width: 100%;
|
||||
padding: 0 2rem;
|
||||
background: var(--next-panel-color-background);
|
||||
padding: 0 4rem;
|
||||
background: var(--theme-panel-color);
|
||||
|
||||
&.sticky {
|
||||
position: sticky;
|
||||
|
||||
@@ -231,7 +231,7 @@
|
||||
|
||||
.text-input__text {
|
||||
overflow: auto;
|
||||
min-height: 2.75rem;
|
||||
min-height: 2.85rem;
|
||||
padding: 0 0.25rem;
|
||||
font-size: 0.875rem;
|
||||
font-weight: 400;
|
||||
|
||||
@@ -14,7 +14,6 @@
|
||||
-->
|
||||
|
||||
<script lang="ts">
|
||||
import { IntlString } from '@hcengineering/platform'
|
||||
import { Markup, RateLimiter } from '@hcengineering/core'
|
||||
import { tick, createEventDispatcher, onDestroy } from 'svelte'
|
||||
import { uploadFile, deleteFile, getCommunicationClient } from '@hcengineering/presentation'
|
||||
@@ -32,12 +31,11 @@
|
||||
import { type TextInputAction, UploadedFile, type PresenceTyping } from '../../types'
|
||||
import TypingPresenter from '../TypingPresenter.svelte'
|
||||
|
||||
export let cardId: CardID | undefined = undefined
|
||||
export let cardType: CardType | undefined = undefined
|
||||
export let cardId: CardID
|
||||
export let cardType: CardType
|
||||
export let message: Message | undefined = undefined
|
||||
export let content: Markup | undefined = undefined
|
||||
export let placeholder: IntlString | undefined = undefined
|
||||
export let placeholderParams: Record<string, any> = {}
|
||||
export let title: string = ''
|
||||
export let onCancel: (() => void) | undefined = undefined
|
||||
export let onSubmit: ((markdown: string, files: UploadedFile[]) => Promise<void>) | undefined = undefined
|
||||
|
||||
@@ -69,13 +67,13 @@
|
||||
|
||||
if (message === undefined) {
|
||||
await createMessage(markdown, filesToLoad)
|
||||
dispatch('sent')
|
||||
} else {
|
||||
await editMessage(message, markdown, filesToLoad)
|
||||
}
|
||||
}
|
||||
|
||||
async function createMessage (markdown: string, files: UploadedFile[]): Promise<void> {
|
||||
if (cardId === undefined || cardType === undefined) return
|
||||
const { id, created } = await communicationClient.createMessage(cardId, cardType, markdown)
|
||||
|
||||
for (const file of files) {
|
||||
@@ -84,7 +82,6 @@
|
||||
}
|
||||
|
||||
async function editMessage (message: Message, markdown: string, files: UploadedFile[]): Promise<void> {
|
||||
if (cardId === undefined) return
|
||||
await communicationClient.updateMessage(cardId, message.id, message.created, markdown)
|
||||
|
||||
for (const file of files) {
|
||||
@@ -204,7 +201,6 @@
|
||||
}
|
||||
|
||||
async function onUpdate (event: CustomEvent<Markup>): Promise<void> {
|
||||
if (cardId === undefined || cardType === undefined) return
|
||||
if (message !== undefined) return
|
||||
const markup = event.detail
|
||||
if (!isEmptyMarkup(markup)) {
|
||||
@@ -235,8 +231,8 @@
|
||||
/>
|
||||
<TextInput
|
||||
{content}
|
||||
{placeholder}
|
||||
{placeholderParams}
|
||||
placeholder={title !== '' ? uiNext.string.MessageIn : undefined}
|
||||
placeholderParams={title !== '' ? { title } : undefined}
|
||||
loading={progress}
|
||||
hasNonTextContent={files.length > 0}
|
||||
actions={[...defaultMessageInputActions, attachAction]}
|
||||
|
||||
@@ -17,13 +17,14 @@
|
||||
import { formatName, getPersonBySocialId, Person } from '@hcengineering/contact'
|
||||
import { createEventDispatcher } from 'svelte'
|
||||
import { getClient } from '@hcengineering/presentation'
|
||||
import { Card } from '@hcengineering/card'
|
||||
import { getCurrentAccount } from '@hcengineering/core'
|
||||
import cardPlugin, { Card } from '@hcengineering/card'
|
||||
import { getCurrentAccount, Ref } from '@hcengineering/core'
|
||||
import { EmojiPopup, getEventPositionElement, showPopup, Action as MenuAction } from '@hcengineering/ui'
|
||||
import { PersonPreviewProvider, personByPersonIdStore } from '@hcengineering/contact-resources'
|
||||
import type { SocialID } from '@hcengineering/communication-types'
|
||||
import { AttachmentPreview } from '@hcengineering/attachment-resources'
|
||||
import { Message, MessageType } from '@hcengineering/communication-types'
|
||||
import { openDoc } from '@hcengineering/view-resources'
|
||||
|
||||
import MessageContentViewer from './MessageContentViewer.svelte'
|
||||
import { AvatarSize } from '../../types'
|
||||
@@ -167,6 +168,16 @@
|
||||
}
|
||||
|
||||
let isActionsOpened = false
|
||||
|
||||
async function handleReply () {
|
||||
const t = message.thread
|
||||
if (t === undefined) return
|
||||
const _id = t.thread
|
||||
const client = getClient()
|
||||
const c = await client.findOne(cardPlugin.class.Card, { _id: _id as Ref<Card> })
|
||||
if (c === undefined) return
|
||||
await openDoc(client.getHierarchy(), c)
|
||||
}
|
||||
</script>
|
||||
|
||||
<!-- svelte-ignore a11y-click-events-have-key-events -->
|
||||
@@ -219,7 +230,8 @@
|
||||
</div>
|
||||
{:else}
|
||||
<MessageInput
|
||||
cardId={message.card}
|
||||
cardId={card._id}
|
||||
cardType={card._class}
|
||||
{message}
|
||||
content={toMarkup(message.content)}
|
||||
onCancel={handleCancelEdit}
|
||||
@@ -244,11 +256,7 @@
|
||||
{/if}
|
||||
{#if replies && message.thread && message.thread.repliesCount > 0}
|
||||
<div class="message__replies overflow-label">
|
||||
<MessageReplies
|
||||
count={message.thread.repliesCount}
|
||||
lastReply={message.thread.lastReply}
|
||||
on:click={() => dispatch('reply', message)}
|
||||
/>
|
||||
<MessageReplies count={message.thread.repliesCount} lastReply={message.thread.lastReply} on:click={handleReply} />
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
@@ -261,7 +269,7 @@
|
||||
align-self: stretch;
|
||||
min-width: 0;
|
||||
position: relative;
|
||||
padding: 1rem 2rem;
|
||||
padding: 1rem 4rem;
|
||||
|
||||
&:hover:not(.noHover) {
|
||||
background: var(--next-message-hover-color-background);
|
||||
@@ -361,6 +369,7 @@
|
||||
gap: 0.375rem;
|
||||
overflow-x: auto;
|
||||
margin-left: 2.75rem;
|
||||
height: 18.75rem;
|
||||
}
|
||||
|
||||
.message__actions {
|
||||
|
||||
@@ -25,9 +25,9 @@
|
||||
export let card: Card
|
||||
export let date: Timestamp
|
||||
export let messages: Message[]
|
||||
export let showDates = true
|
||||
export let separatorDate: Date | undefined = undefined
|
||||
export let separatorDiv: HTMLDivElement | undefined | null = undefined
|
||||
export let readonly = false
|
||||
|
||||
const me = getCurrentAccount()
|
||||
|
||||
@@ -40,15 +40,16 @@
|
||||
</script>
|
||||
|
||||
<div class="messages-group" id={date.toString()}>
|
||||
{#if showDates}
|
||||
<DateSeparator {date} />
|
||||
{#if separatorIndex === 0}
|
||||
<MessagesSeparator bind:element={separatorDiv} />
|
||||
{/if}
|
||||
<DateSeparator {date} />
|
||||
<div class="messages-group__messages">
|
||||
{#each messages as message, index (message.id)}
|
||||
{#if index === separatorIndex}
|
||||
{#if separatorIndex !== 0 && index === separatorIndex}
|
||||
<MessagesSeparator bind:element={separatorDiv} />
|
||||
{/if}
|
||||
<MessagePresenter {message} {card} on:reply />
|
||||
<MessagePresenter {message} {card} editable={!readonly} on:reply />
|
||||
{/each}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
+3
-4
@@ -13,13 +13,12 @@
|
||||
// limitations under the License.
|
||||
-->
|
||||
<script lang="ts">
|
||||
import { Label } from '@hcengineering/ui-next'
|
||||
|
||||
import chat from '../plugin'
|
||||
import Label from '../Label.svelte'
|
||||
import uiNext from '../../plugin'
|
||||
</script>
|
||||
|
||||
<div class="loader">
|
||||
<Label label={chat.string.Loading} />
|
||||
<Label label={uiNext.string.Loading} />
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
@@ -16,11 +16,15 @@
|
||||
export let element: HTMLDivElement | undefined | null = undefined
|
||||
</script>
|
||||
|
||||
<div class="w-full text-sm flex-center whitespace-nowrap" bind:this={element}>
|
||||
<div class="w-full text-sm flex-center whitespace-nowrap container" bind:this={element}>
|
||||
<div class="line mr-3" />
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.container {
|
||||
padding: 0 4rem;
|
||||
}
|
||||
|
||||
.line {
|
||||
position: relative;
|
||||
width: 100%;
|
||||
|
||||
@@ -32,3 +32,4 @@ export { default as NavigationList } from './components/NavigationList.svelte'
|
||||
export { default as Section } from './components/Section.svelte'
|
||||
export { default as Divider } from './components/Divider.svelte'
|
||||
export { default as Button } from './components/Button.svelte'
|
||||
export { default as MessagesLoading } from './components/message/MessagesLoading.svelte'
|
||||
|
||||
@@ -47,7 +47,9 @@ export const uiNext = plugin(uiNextId, {
|
||||
Yesterday: '' as IntlString,
|
||||
YesterdayAt: '' as IntlString,
|
||||
AndMore: '' as IntlString,
|
||||
IsTyping: '' as IntlString
|
||||
IsTyping: '' as IntlString,
|
||||
Loading: '' as IntlString,
|
||||
MessageIn: '' as IntlString
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
@@ -21,19 +21,10 @@ import { getCommunicationClient } from '@hcengineering/presentation'
|
||||
|
||||
import IconAt from './components/icons/IconAt.svelte'
|
||||
import IconEmoji from './components/icons/IconEmoji.svelte'
|
||||
import IconTextFont from './components/icons/IconTextFont.svelte'
|
||||
import { type TextInputAction } from './types'
|
||||
import uiNext from './plugin'
|
||||
|
||||
export const defaultMessageInputActions: TextInputAction[] = [
|
||||
{
|
||||
label: uiNext.string.ShowFormatting,
|
||||
icon: IconTextFont,
|
||||
action: (_element, editorHandler) => {
|
||||
// TODO: implement
|
||||
},
|
||||
order: 2000
|
||||
},
|
||||
{
|
||||
label: uiNext.string.Emoji,
|
||||
icon: IconEmoji,
|
||||
|
||||
@@ -120,6 +120,7 @@
|
||||
on:validate
|
||||
on:submit
|
||||
on:select
|
||||
on:loaded
|
||||
>
|
||||
<slot />
|
||||
</svelte:component>
|
||||
@@ -140,6 +141,7 @@
|
||||
on:validate
|
||||
on:submit
|
||||
on:select
|
||||
on:loaded
|
||||
/>
|
||||
{/if}
|
||||
</ErrorBoundary>
|
||||
|
||||
@@ -51,7 +51,7 @@
|
||||
"@hcengineering/ui-next": "^0.6.0",
|
||||
"@hcengineering/view": "^0.6.13",
|
||||
"@hcengineering/view-resources": "^0.6.0",
|
||||
"@hcengineering/communication-types": "0.1.172",
|
||||
"@hcengineering/communication-types": "0.1.174",
|
||||
"svelte": "^4.2.19"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,131 +0,0 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { SortingOrder } from '@hcengineering/core'
|
||||
import { createMessagesQuery } from '@hcengineering/presentation'
|
||||
import { Grid, Section, Spinner } from '@hcengineering/ui'
|
||||
import { onDestroy, onMount } from 'svelte'
|
||||
import activity from '@hcengineering/activity'
|
||||
import { Card } from '@hcengineering/card'
|
||||
import { MessagePresenter, MessageInput } from '@hcengineering/ui-next'
|
||||
import { Message, Window } from '@hcengineering/communication-types'
|
||||
|
||||
export let object: Card
|
||||
export let showInput: boolean = true
|
||||
export let focusIndex: number = -1
|
||||
export let boundary: HTMLElement | undefined = undefined
|
||||
|
||||
const query = createMessagesQuery()
|
||||
let isLoading = true
|
||||
let isNextLoading = false
|
||||
|
||||
let messages: Message[] = []
|
||||
let window: Window<Message> | undefined
|
||||
|
||||
$: query.query(
|
||||
{
|
||||
card: object._id,
|
||||
replies: true,
|
||||
files: true,
|
||||
reactions: true,
|
||||
order: SortingOrder.Ascending,
|
||||
limit: 100
|
||||
},
|
||||
(res) => {
|
||||
messages = res.getResult()
|
||||
isLoading = false
|
||||
window = res
|
||||
}
|
||||
)
|
||||
|
||||
function handleScroll (event: Event): void {
|
||||
const element = event.target as HTMLElement
|
||||
if (element != null && window != null && window.hasNextPage() && !isNextLoading) {
|
||||
const isAtBottom = element.scrollTop + element.clientHeight >= element.scrollHeight - 200
|
||||
if (isAtBottom) {
|
||||
isNextLoading = true
|
||||
void window.loadNextPage().finally(() => {
|
||||
isNextLoading = false
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
onMount(() => {
|
||||
if (!boundary) return
|
||||
boundary.addEventListener('scroll', handleScroll)
|
||||
})
|
||||
|
||||
onDestroy(() => {
|
||||
if (!boundary) return
|
||||
boundary.removeEventListener('scroll', handleScroll)
|
||||
})
|
||||
</script>
|
||||
|
||||
<Section label={activity.string.Activity} icon={activity.icon.Activity}>
|
||||
<svelte:fragment slot="header">
|
||||
{#if isLoading}
|
||||
<div class="ml-1">
|
||||
<Spinner size="small" />
|
||||
</div>
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="content">
|
||||
<div class="p-activity select-text" id={activity.string.Activity}>
|
||||
{#if messages.length}
|
||||
<Grid column={1} rowGap={1}>
|
||||
{#each messages as message (message.id)}
|
||||
<MessagePresenter {message} card={object} />
|
||||
{/each}
|
||||
</Grid>
|
||||
{/if}
|
||||
</div>
|
||||
{#if showInput}
|
||||
<div class="ref-input oldest-first">
|
||||
<MessageInput cardId={object._id} cardType={object._class} placeholder={activity.string.Message} />
|
||||
</div>
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
</Section>
|
||||
|
||||
<style lang="scss">
|
||||
.ref-input {
|
||||
flex-shrink: 0;
|
||||
|
||||
&.newest-first {
|
||||
margin-bottom: 1rem;
|
||||
padding-top: 1rem;
|
||||
}
|
||||
|
||||
&.oldest-first {
|
||||
padding-bottom: 2.5rem;
|
||||
}
|
||||
}
|
||||
|
||||
.p-activity {
|
||||
&.newest-first {
|
||||
padding-bottom: 1.75rem;
|
||||
}
|
||||
|
||||
&:not(.newest-first) {
|
||||
margin: 1.75rem 0;
|
||||
}
|
||||
}
|
||||
|
||||
:global(.grid .msgactivity-container.showIcon:last-child::after) {
|
||||
content: none;
|
||||
}
|
||||
</style>
|
||||
@@ -16,7 +16,6 @@
|
||||
import { type Resources } from '@hcengineering/platform'
|
||||
|
||||
import Activity from './components/Activity.svelte'
|
||||
import NewActivity from './components/NewActivity.svelte'
|
||||
import ActivityMessagePresenter from './components/activity-message/ActivityMessagePresenter.svelte'
|
||||
import DocUpdateMessagePresenter from './components/doc-update-message/DocUpdateMessagePresenter.svelte'
|
||||
import ActivityInfoMessagePresenter from './components/activity-info-message/ActivityInfoMessagePresenter.svelte'
|
||||
@@ -68,7 +67,6 @@ export { default as BasePreview } from './components/BasePreview.svelte'
|
||||
export default async (): Promise<Resources> => ({
|
||||
component: {
|
||||
Activity,
|
||||
NewActivity,
|
||||
ActivityMessagePresenter,
|
||||
DocUpdateMessagePresenter,
|
||||
ReactionPresenter,
|
||||
|
||||
@@ -326,7 +326,6 @@ export default plugin(activityId, {
|
||||
},
|
||||
component: {
|
||||
Activity: '' as AnyComponent,
|
||||
NewActivity: '' as AnyComponent,
|
||||
ActivityMessagePresenter: '' as AnyComponent,
|
||||
DocUpdateMessagePresenter: '' as AnyComponent,
|
||||
ActivityInfoMessagePresenter: '' as AnyComponent,
|
||||
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "Vybrat typ",
|
||||
"CreateSpace": "Vytvořit prostor",
|
||||
"NumberTypes": "{count, plural, one {# typ} few {# typy} other {# typů}}",
|
||||
"Labels": "Štítky"
|
||||
"Labels": "Štítky",
|
||||
"Properties": "Vlastnosti"
|
||||
}
|
||||
}
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "Typ auswählen",
|
||||
"CreateSpace": "Raum erstellen",
|
||||
"NumberTypes": "{count, plural, one {# typ} other {# typen}}",
|
||||
"Labels": "Labels"
|
||||
"Labels": "Labels",
|
||||
"Properties": "Eigenschaften"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "Select Type",
|
||||
"CreateSpace": "Create space",
|
||||
"NumberTypes": "{count, plural, one {# type} other {# types}}",
|
||||
"Labels": "Labels"
|
||||
"Labels": "Labels",
|
||||
"Properties": "Properties"
|
||||
}
|
||||
}
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "Seleccionar tipo",
|
||||
"CreateSpace": "Crear espacio",
|
||||
"NumberTypes": "{count, plural, one {# tipo} other {# tipos}}",
|
||||
"Labels": "Etiquetas"
|
||||
"Labels": "Etiquetas",
|
||||
"Properties": "Propiedades"
|
||||
}
|
||||
}
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "Sélectionner le type",
|
||||
"CreateSpace": "Créer un espace",
|
||||
"NumberTypes": "{count, plural, one {# type} other {# types}}",
|
||||
"Labels": "Étiquettes"
|
||||
"Labels": "Étiquettes",
|
||||
"Properties": "Propriétés"
|
||||
}
|
||||
}
|
||||
@@ -35,6 +35,7 @@
|
||||
"MasterDetailViews": "Viste Master-Detail",
|
||||
"SelectType": "Seleziona il tipo",
|
||||
"CreateSpace": "Crea spazio",
|
||||
"Labels": "Etichette"
|
||||
"Labels": "Etichette",
|
||||
"Properties": "Proprietà"
|
||||
}
|
||||
}
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "タイプを選択",
|
||||
"CreateSpace": "スペースを作成",
|
||||
"NumberTypes": "{count, plural, one {# タイプ} other {# タイプ}}",
|
||||
"Labels": "ラベル"
|
||||
"Labels": "ラベル",
|
||||
"Properties": "プロパティ"
|
||||
}
|
||||
}
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "Selecionar tipo",
|
||||
"CreateSpace": "Criar espaço",
|
||||
"NumberTypes": "{count, plural, one {# tipo} other {# tipos}}",
|
||||
"Labels": "Etiquetas"
|
||||
"Labels": "Etiquetas",
|
||||
"Properties": "Propriedades"
|
||||
}
|
||||
}
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "Выбрать тип",
|
||||
"CreateSpace": "Создать пространство",
|
||||
"NumberTypes": "{count, plural, one {# тип} few {# типа} other {# типов}}",
|
||||
"Labels": "Метки"
|
||||
"Labels": "Метки",
|
||||
"Properties": "Свойства"
|
||||
}
|
||||
}
|
||||
@@ -36,6 +36,7 @@
|
||||
"SelectType": "选择类型",
|
||||
"CreateSpace": "创建空间",
|
||||
"NumberTypes": "{count, plural, one {# 类型} other {# 类型}}",
|
||||
"Labels": "标签"
|
||||
"Labels": "标签",
|
||||
"Properties": "属性"
|
||||
}
|
||||
}
|
||||
@@ -39,8 +39,9 @@
|
||||
"typescript": "^5.3.3"
|
||||
},
|
||||
"dependencies": {
|
||||
"@hcengineering/presence": "^0.6.0",
|
||||
"@hcengineering/presentation": "^0.6.3",
|
||||
"@hcengineering/communication-types": "0.1.172",
|
||||
"@hcengineering/communication-types": "0.1.174",
|
||||
"@hcengineering/core": "^0.6.32",
|
||||
"@hcengineering/ui": "^0.6.15",
|
||||
"@hcengineering/setting": "^0.6.17",
|
||||
|
||||
@@ -0,0 +1,104 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { closeWidget, WidgetState } from '@hcengineering/workbench-resources'
|
||||
import { Widget } from '@hcengineering/workbench'
|
||||
import { createQuery, createNotificationContextsQuery } from '@hcengineering/presentation'
|
||||
import { NotificationContext } from '@hcengineering/communication-types'
|
||||
import { createEventDispatcher } from 'svelte'
|
||||
import { Card } from '@hcengineering/card'
|
||||
import { Ref } from '@hcengineering/core'
|
||||
import { Button, Header, IconClose } from '@hcengineering/ui'
|
||||
|
||||
import EditCardTableOfContents from './EditCardTableOfContents.svelte'
|
||||
import card from '../plugin'
|
||||
import { CardWidgetData } from '../utils'
|
||||
import CardPresenter from './CardPresenter.svelte'
|
||||
|
||||
export let widget: Widget | undefined
|
||||
export let widgetState: WidgetState | undefined
|
||||
export let height: string
|
||||
export let width: string
|
||||
|
||||
const query = createQuery()
|
||||
const contextsQuery = createNotificationContextsQuery()
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
let data: CardWidgetData | undefined = undefined
|
||||
|
||||
let doc: Card | undefined = undefined
|
||||
let context: NotificationContext | undefined = undefined
|
||||
let isContextLoaded = false
|
||||
|
||||
$: data = widgetState?.data as CardWidgetData
|
||||
|
||||
$: if (widget === undefined || data?._id === undefined) {
|
||||
closeWidget(card.ids.CardWidget as Ref<Widget>)
|
||||
}
|
||||
|
||||
$: data._id &&
|
||||
query.query(
|
||||
card.class.Card,
|
||||
{ _id: data._id },
|
||||
(res) => {
|
||||
if (res.length === 0) {
|
||||
closeWidget(card.ids.CardWidget as Ref<Widget>)
|
||||
} else {
|
||||
doc = res[0]
|
||||
}
|
||||
},
|
||||
{ limit: 1 }
|
||||
)
|
||||
|
||||
$: data._id &&
|
||||
contextsQuery.query({ card: data._id, limit: 1 }, (res) => {
|
||||
context = res.getResult()[0]
|
||||
isContextLoaded = true
|
||||
})
|
||||
</script>
|
||||
|
||||
{#if widget && data?._id}
|
||||
<div class="card-widget" style:width style:height>
|
||||
<Header type={'type-panel'} noPrint adaptive="disabled">
|
||||
<svelte:fragment slot="beforeTitle">
|
||||
<Button
|
||||
id={'btnPClose'}
|
||||
focusIndex={10001}
|
||||
icon={IconClose}
|
||||
iconProps={{ size: 'medium' }}
|
||||
kind={'icon'}
|
||||
noPrint
|
||||
on:click={() => {
|
||||
dispatch('close')
|
||||
}}
|
||||
/>
|
||||
</svelte:fragment>
|
||||
<CardPresenter value={doc} noUnderline />
|
||||
</Header>
|
||||
{#if doc}
|
||||
<EditCardTableOfContents {doc} {context} {isContextLoaded} readonly={false} />
|
||||
{/if}
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
.card-widget {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
min-height: 0;
|
||||
}
|
||||
</style>
|
||||
@@ -22,6 +22,7 @@
|
||||
export let doc: Card
|
||||
export let readonly: boolean = false
|
||||
export let content: HTMLElement
|
||||
export let showToc: boolean = true
|
||||
|
||||
const client = getClient()
|
||||
const hierarchy = client.getHierarchy()
|
||||
@@ -43,4 +44,4 @@
|
||||
/>
|
||||
{/each}
|
||||
|
||||
<Description {doc} {readonly} bind:content minHeight={isFile ? '15vh' : '25vh'} />
|
||||
<Description {doc} {readonly} {showToc} bind:content minHeight={isFile ? '15vh' : '25vh'} on:loaded on:headings />
|
||||
|
||||
@@ -23,14 +23,18 @@
|
||||
import { navigate } from '@hcengineering/ui'
|
||||
import view from '@hcengineering/view'
|
||||
import { getObjectLinkFragment } from '@hcengineering/view-resources'
|
||||
import { createEventDispatcher } from 'svelte'
|
||||
|
||||
import ContentEditor from './ContentEditor.svelte'
|
||||
|
||||
export let doc: Card
|
||||
export let readonly: boolean = false
|
||||
export let content: HTMLElement
|
||||
export let minHeight: '15vh' | '25vh' = '25vh'
|
||||
export let showToc: boolean = true
|
||||
|
||||
const client = getClient()
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
let editor: ContentEditor
|
||||
|
||||
@@ -70,18 +74,20 @@
|
||||
</script>
|
||||
|
||||
<div class="content select-text mt-4">
|
||||
<div class="toc-container">
|
||||
<div class="toc">
|
||||
<TableOfContents
|
||||
items={headings}
|
||||
on:select={(evt) => {
|
||||
const heading = evt.detail
|
||||
const element = window.document.getElementById(heading.id)
|
||||
element?.scrollIntoView({ behavior: 'smooth', block: 'start' })
|
||||
}}
|
||||
/>
|
||||
{#if showToc}
|
||||
<div class="toc-container">
|
||||
<div class="toc">
|
||||
<TableOfContents
|
||||
items={headings}
|
||||
on:select={(evt) => {
|
||||
const heading = evt.detail
|
||||
const element = window.document.getElementById(heading.id)
|
||||
element?.scrollIntoView({ behavior: 'smooth', block: 'start' })
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
{#key doc._id}
|
||||
<ContentEditor
|
||||
@@ -96,6 +102,7 @@
|
||||
}}
|
||||
on:headings={(evt) => {
|
||||
headings = evt.detail
|
||||
dispatch('headings', headings)
|
||||
}}
|
||||
on:open-document={async (event) => {
|
||||
const doc = await client.findOne(event.detail._class, { _id: event.detail._id })
|
||||
@@ -105,6 +112,7 @@
|
||||
}
|
||||
}}
|
||||
bind:this={editor}
|
||||
on:loaded
|
||||
/>
|
||||
{/key}
|
||||
</div>
|
||||
|
||||
@@ -15,193 +15,25 @@
|
||||
//
|
||||
-->
|
||||
<script lang="ts">
|
||||
import { Analytics } from '@hcengineering/analytics'
|
||||
import { Attachments } from '@hcengineering/attachment-resources'
|
||||
import { Card, CardEvents } from '@hcengineering/card'
|
||||
import { Doc, Mixin, Ref, WithLookup } from '@hcengineering/core'
|
||||
import notification from '@hcengineering/notification'
|
||||
import { Panel } from '@hcengineering/panel'
|
||||
import { getResource } from '@hcengineering/platform'
|
||||
import { ComponentExtensions, createQuery, getClient } from '@hcengineering/presentation'
|
||||
import {
|
||||
Button,
|
||||
EditBox,
|
||||
FocusHandler,
|
||||
IconMoreH,
|
||||
createFocusManager,
|
||||
getCurrentLocation,
|
||||
navigate
|
||||
} from '@hcengineering/ui'
|
||||
import view from '@hcengineering/view'
|
||||
import { ParentsNavigator, RelationsEditor, getDocMixins, showMenu } from '@hcengineering/view-resources'
|
||||
import { createEventDispatcher, onDestroy, onMount } from 'svelte'
|
||||
import card from '../plugin'
|
||||
import CardAttributeEditor from './CardAttributeEditor.svelte'
|
||||
import CardPresenter from './CardPresenter.svelte'
|
||||
import Childs from './Childs.svelte'
|
||||
import Content from './Content.svelte'
|
||||
import TagsEditor from './TagsEditor.svelte'
|
||||
import { Ref } from '@hcengineering/core'
|
||||
import { onMount } from 'svelte'
|
||||
import { Analytics } from '@hcengineering/analytics'
|
||||
|
||||
import EditCardNew from './EditCardNew.svelte'
|
||||
|
||||
export let _id: Ref<Card>
|
||||
export let readonly: boolean = false
|
||||
export let embedded: boolean = false
|
||||
|
||||
let useMaxWidth = getUseMaxWidth()
|
||||
$: saveUseMaxWidth(useMaxWidth)
|
||||
export let allowClose: boolean = true
|
||||
|
||||
export function canClose (): boolean {
|
||||
return false
|
||||
}
|
||||
|
||||
let lastId: Ref<Doc> = _id
|
||||
const query = createQuery()
|
||||
const dispatch = createEventDispatcher()
|
||||
const client = getClient()
|
||||
|
||||
let doc: WithLookup<Card> | undefined
|
||||
let title = ''
|
||||
let innerWidth: number
|
||||
|
||||
const notificationClient = getResource(notification.function.GetInboxNotificationsClient).then((res) => res())
|
||||
|
||||
$: read(_id)
|
||||
function read (_id: Ref<Doc>): void {
|
||||
if (lastId !== _id) {
|
||||
const prev = lastId
|
||||
lastId = _id
|
||||
void notificationClient.then((client) => client.readDoc(prev))
|
||||
}
|
||||
}
|
||||
|
||||
onDestroy(async () => {
|
||||
void notificationClient.then((client) => client.readDoc(_id))
|
||||
})
|
||||
|
||||
$: _id !== undefined &&
|
||||
query.query(card.class.Card, { _id }, async (result) => {
|
||||
if (result.length > 0) {
|
||||
;[doc] = result
|
||||
title = doc?.title ?? ''
|
||||
} else {
|
||||
const loc = getCurrentLocation()
|
||||
loc.path.length = 3
|
||||
navigate(loc)
|
||||
}
|
||||
})
|
||||
|
||||
$: canSave = title.trim().length > 0
|
||||
|
||||
async function saveTitle (ev: Event): Promise<void> {
|
||||
ev.preventDefault()
|
||||
|
||||
if (doc === undefined || !canSave) {
|
||||
return
|
||||
}
|
||||
|
||||
const nameTrimmed = title.trim()
|
||||
|
||||
if (nameTrimmed.length > 0 && nameTrimmed !== doc.title) {
|
||||
await client.update(doc, { title: nameTrimmed })
|
||||
}
|
||||
}
|
||||
|
||||
function getUseMaxWidth (): boolean {
|
||||
const useMaxWidth = localStorage.getItem('document.useMaxWidth')
|
||||
return useMaxWidth === 'true'
|
||||
}
|
||||
|
||||
function saveUseMaxWidth (useMaxWidth: boolean): void {
|
||||
localStorage.setItem('document.useMaxWidth', useMaxWidth.toString())
|
||||
}
|
||||
|
||||
onMount(() => {
|
||||
Analytics.handleEvent(CardEvents.CardOpened, { id: _id })
|
||||
})
|
||||
|
||||
let content: HTMLElement
|
||||
|
||||
const manager = createFocusManager()
|
||||
|
||||
let mixins: Array<Mixin<Doc>> = []
|
||||
|
||||
$: mixins = doc !== undefined ? getDocMixins(doc) : []
|
||||
</script>
|
||||
|
||||
<FocusHandler {manager} />
|
||||
|
||||
{#if doc !== undefined}
|
||||
<Panel
|
||||
object={doc}
|
||||
allowClose={!embedded}
|
||||
isAside={false}
|
||||
isHeader={false}
|
||||
isSub={false}
|
||||
bind:useMaxWidth
|
||||
printHeader={false}
|
||||
{embedded}
|
||||
adaptive={'default'}
|
||||
bind:content
|
||||
bind:innerWidth
|
||||
floatAside={false}
|
||||
newActivity
|
||||
on:open
|
||||
on:close={() => dispatch('close')}
|
||||
>
|
||||
<svelte:fragment slot="title">
|
||||
<ParentsNavigator element={doc} />
|
||||
<CardPresenter value={doc} noUnderline />
|
||||
</svelte:fragment>
|
||||
|
||||
<div class="container">
|
||||
<div class="title flex-row-center">
|
||||
<EditBox focusIndex={1} bind:value={title} placeholder={card.string.Card} on:blur={(evt) => saveTitle(evt)} />
|
||||
</div>
|
||||
|
||||
<TagsEditor {doc} />
|
||||
|
||||
<CardAttributeEditor value={doc} {mixins} {readonly} ignoreKeys={['title', 'content', 'parent']} />
|
||||
|
||||
<Content {doc} {readonly} bind:content />
|
||||
</div>
|
||||
|
||||
<ComponentExtensions
|
||||
extension={card.extensions.EditCardExtension}
|
||||
props={{
|
||||
card: doc
|
||||
}}
|
||||
/>
|
||||
|
||||
<Childs object={doc} {readonly} />
|
||||
<RelationsEditor object={doc} {readonly} />
|
||||
|
||||
<Attachments objectId={doc._id} _class={doc._class} space={doc.space} attachments={doc.attachments ?? 0} />
|
||||
|
||||
<svelte:fragment slot="utils">
|
||||
{#if !readonly}
|
||||
<Button
|
||||
icon={IconMoreH}
|
||||
iconProps={{ size: 'medium' }}
|
||||
kind={'icon'}
|
||||
dataId={'btnMoreActions'}
|
||||
on:click={(e) => {
|
||||
showMenu(e, { object: doc, excludedActions: [view.action.Open] })
|
||||
}}
|
||||
/>
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
</Panel>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
.container {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
margin: auto;
|
||||
}
|
||||
.title {
|
||||
font-size: 2.25rem;
|
||||
margin-top: 1.75rem;
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
</style>
|
||||
<EditCardNew {_id} {readonly} {embedded} {allowClose} on:close on:open />
|
||||
|
||||
@@ -0,0 +1,197 @@
|
||||
<!--
|
||||
//
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { Ref, WithLookup } from '@hcengineering/core'
|
||||
import {
|
||||
Button,
|
||||
Component,
|
||||
createFocusManager,
|
||||
EditBox,
|
||||
FocusHandler,
|
||||
getCurrentLocation,
|
||||
IconDetailsFilled,
|
||||
IconMoreH,
|
||||
navigate,
|
||||
Panel
|
||||
} from '@hcengineering/ui'
|
||||
import presence from '@hcengineering/presence'
|
||||
import { createQuery, createNotificationContextsQuery, getClient } from '@hcengineering/presentation'
|
||||
import { ParentsNavigator, showMenu } from '@hcengineering/view-resources'
|
||||
import view from '@hcengineering/view'
|
||||
import { NotificationContext } from '@hcengineering/communication-types'
|
||||
|
||||
import card from '../plugin'
|
||||
import CardPresenter from './CardPresenter.svelte'
|
||||
import { openCardInSidebar } from '../utils'
|
||||
import EditCardTableOfContents from './EditCardTableOfContents.svelte'
|
||||
import { translate } from '@hcengineering/platform'
|
||||
import { makeRank } from '@hcengineering/rank'
|
||||
import TagsEditor from './TagsEditor.svelte'
|
||||
|
||||
export let _id: Ref<Card>
|
||||
export let readonly: boolean = false
|
||||
export let embedded: boolean = false
|
||||
export let allowClose: boolean = true
|
||||
|
||||
const manager = createFocusManager()
|
||||
const query = createQuery()
|
||||
const contextsQuery = createNotificationContextsQuery()
|
||||
|
||||
let doc: WithLookup<Card> | undefined
|
||||
let context: NotificationContext | undefined = undefined
|
||||
let isContextLoaded = false
|
||||
|
||||
let title: string = ''
|
||||
let prevId: Ref<Card> = _id
|
||||
|
||||
$: if (prevId !== _id) {
|
||||
prevId = _id
|
||||
context = undefined
|
||||
isContextLoaded = false
|
||||
}
|
||||
|
||||
$: query.query(card.class.Card, { _id }, async (result) => {
|
||||
if (result.length > 0) {
|
||||
;[doc] = result
|
||||
title = doc.title
|
||||
} else {
|
||||
const loc = getCurrentLocation()
|
||||
loc.path.length = 3
|
||||
navigate(loc)
|
||||
}
|
||||
})
|
||||
|
||||
$: contextsQuery.query({ card: _id, limit: 1 }, (res) => {
|
||||
context = res.getResult()[0]
|
||||
isContextLoaded = true
|
||||
})
|
||||
|
||||
async function saveTitle (ev: Event): Promise<void> {
|
||||
ev.preventDefault()
|
||||
const client = getClient()
|
||||
|
||||
const canSave = title.trim().length > 0
|
||||
if (doc === undefined || !canSave) {
|
||||
return
|
||||
}
|
||||
|
||||
const nameTrimmed = title.trim()
|
||||
|
||||
if (nameTrimmed.length > 0 && nameTrimmed !== doc.title) {
|
||||
await client.update(doc, { title: nameTrimmed })
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<FocusHandler {manager} />
|
||||
{#if doc !== undefined}
|
||||
<Panel isAside={false} isHeader={false} {embedded} {allowClose} adaptive="disabled" on:open on:close>
|
||||
<div class="main-content clear-mins">
|
||||
{#key doc._id}
|
||||
<EditCardTableOfContents {doc} {readonly} {context} {isContextLoaded} />
|
||||
{/key}
|
||||
</div>
|
||||
|
||||
<svelte:fragment slot="title">
|
||||
<ParentsNavigator element={doc} />
|
||||
<div class="title flex-row-center">
|
||||
<EditBox focusIndex={1} bind:value={title} placeholder={card.string.Card} on:blur={saveTitle} />
|
||||
</div>
|
||||
<TagsEditor {doc} />
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="presence">
|
||||
<Component is={presence.component.PresenceAvatars} props={{ object: doc, size: 'x-small', limit: 5 }} />
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="pre-utils">
|
||||
<slot name="pre-utils" />
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="panel-footer">
|
||||
<slot name="panel-footer" />
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="utils">
|
||||
<!-- <Button-->
|
||||
<!-- icon={IconDetailsFilled}-->
|
||||
<!-- iconProps={{ size: 'medium' }}-->
|
||||
<!-- kind="icon"-->
|
||||
<!-- on:click={() => {-->
|
||||
<!-- if (doc != null) {-->
|
||||
<!-- void openCardInSidebar(doc._id, doc)-->
|
||||
<!-- }-->
|
||||
<!-- }}-->
|
||||
<!-- />-->
|
||||
|
||||
{#if !readonly}
|
||||
<Button
|
||||
icon={IconMoreH}
|
||||
iconProps={{ size: 'medium' }}
|
||||
kind="icon"
|
||||
dataId="btnMoreActions"
|
||||
on:click={(e) => {
|
||||
showMenu(e, { object: doc, excludedActions: [view.action.Open] })
|
||||
}}
|
||||
/>
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="header">
|
||||
{#if $$slots.header}
|
||||
<div class="header-row between">
|
||||
{#if $$slots.header}
|
||||
<slot name="header" />
|
||||
{/if}
|
||||
<div class="buttons-group xsmall-gap ml-4" style:align-self={'flex-start'}>
|
||||
<slot name="tools" />
|
||||
</div>
|
||||
</div>
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="post-utils">
|
||||
<slot name="post-utils" />
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="extra">
|
||||
<slot name="extra" />
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="page-header">
|
||||
<slot name="page-header" />
|
||||
</svelte:fragment>
|
||||
|
||||
<svelte:fragment slot="page-footer">
|
||||
<slot name="page-footer" />
|
||||
</svelte:fragment>
|
||||
</Panel>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
.main-content {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
flex: 1;
|
||||
}
|
||||
.title {
|
||||
font-size: 1rem;
|
||||
flex: 1;
|
||||
min-width: 10rem;
|
||||
}
|
||||
</style>
|
||||
@@ -0,0 +1,198 @@
|
||||
<!--
|
||||
//
|
||||
// Copyright © 2025 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 { Attachments } from '@hcengineering/attachment-resources'
|
||||
import { Card } from '@hcengineering/card'
|
||||
import { Doc, Mixin, Ref, WithLookup } from '@hcengineering/core'
|
||||
import notification from '@hcengineering/notification'
|
||||
import { Panel } from '@hcengineering/panel'
|
||||
import { getResource } from '@hcengineering/platform'
|
||||
import { ComponentExtensions, createQuery, getClient } from '@hcengineering/presentation'
|
||||
import {
|
||||
Button,
|
||||
EditBox,
|
||||
FocusHandler,
|
||||
IconMoreH,
|
||||
createFocusManager,
|
||||
getCurrentLocation,
|
||||
navigate
|
||||
} from '@hcengineering/ui'
|
||||
import view from '@hcengineering/view'
|
||||
import { ParentsNavigator, RelationsEditor, getDocMixins, showMenu } from '@hcengineering/view-resources'
|
||||
import { createEventDispatcher, onDestroy } from 'svelte'
|
||||
|
||||
import card from '../plugin'
|
||||
import CardAttributeEditor from './CardAttributeEditor.svelte'
|
||||
import CardPresenter from './CardPresenter.svelte'
|
||||
import Childs from './Childs.svelte'
|
||||
import Content from './Content.svelte'
|
||||
import TagsEditor from './TagsEditor.svelte'
|
||||
|
||||
export let _id: Ref<Card>
|
||||
export let readonly: boolean = false
|
||||
export let embedded: boolean = false
|
||||
|
||||
let useMaxWidth = getUseMaxWidth()
|
||||
$: saveUseMaxWidth(useMaxWidth)
|
||||
|
||||
let lastId: Ref<Doc> = _id
|
||||
const query = createQuery()
|
||||
const dispatch = createEventDispatcher()
|
||||
const client = getClient()
|
||||
|
||||
let doc: WithLookup<Card> | undefined
|
||||
let title = ''
|
||||
let innerWidth: number
|
||||
|
||||
const notificationClient = getResource(notification.function.GetInboxNotificationsClient).then((res) => res())
|
||||
|
||||
$: read(_id)
|
||||
function read (_id: Ref<Doc>): void {
|
||||
if (lastId !== _id) {
|
||||
const prev = lastId
|
||||
lastId = _id
|
||||
void notificationClient.then((client) => client.readDoc(prev))
|
||||
}
|
||||
}
|
||||
|
||||
onDestroy(async () => {
|
||||
void notificationClient.then((client) => client.readDoc(_id))
|
||||
})
|
||||
|
||||
$: _id !== undefined &&
|
||||
query.query(card.class.Card, { _id }, async (result) => {
|
||||
if (result.length > 0) {
|
||||
;[doc] = result
|
||||
title = doc?.title ?? ''
|
||||
} else {
|
||||
const loc = getCurrentLocation()
|
||||
loc.path.length = 3
|
||||
navigate(loc)
|
||||
}
|
||||
})
|
||||
|
||||
$: canSave = title.trim().length > 0
|
||||
|
||||
async function saveTitle (ev: Event): Promise<void> {
|
||||
ev.preventDefault()
|
||||
|
||||
if (doc === undefined || !canSave) {
|
||||
return
|
||||
}
|
||||
|
||||
const nameTrimmed = title.trim()
|
||||
|
||||
if (nameTrimmed.length > 0 && nameTrimmed !== doc.title) {
|
||||
await client.update(doc, { title: nameTrimmed })
|
||||
}
|
||||
}
|
||||
|
||||
function getUseMaxWidth (): boolean {
|
||||
const useMaxWidth = localStorage.getItem('document.useMaxWidth')
|
||||
return useMaxWidth === 'true'
|
||||
}
|
||||
|
||||
function saveUseMaxWidth (useMaxWidth: boolean): void {
|
||||
localStorage.setItem('document.useMaxWidth', useMaxWidth.toString())
|
||||
}
|
||||
|
||||
let content: HTMLElement
|
||||
|
||||
const manager = createFocusManager()
|
||||
|
||||
let mixins: Array<Mixin<Doc>> = []
|
||||
|
||||
$: mixins = doc !== undefined ? getDocMixins(doc) : []
|
||||
</script>
|
||||
|
||||
<FocusHandler {manager} />
|
||||
|
||||
{#if doc !== undefined}
|
||||
<Panel
|
||||
object={doc}
|
||||
allowClose={!embedded}
|
||||
isAside={false}
|
||||
isHeader={false}
|
||||
isSub={false}
|
||||
bind:useMaxWidth
|
||||
printHeader={false}
|
||||
{embedded}
|
||||
adaptive={'default'}
|
||||
bind:content
|
||||
bind:innerWidth
|
||||
floatAside={false}
|
||||
on:open
|
||||
on:close={() => dispatch('close')}
|
||||
>
|
||||
<svelte:fragment slot="title">
|
||||
<ParentsNavigator element={doc} />
|
||||
<CardPresenter value={doc} noUnderline />
|
||||
</svelte:fragment>
|
||||
|
||||
<div class="container">
|
||||
<div class="title flex-row-center">
|
||||
<EditBox focusIndex={1} bind:value={title} placeholder={card.string.Card} on:blur={(evt) => saveTitle(evt)} />
|
||||
</div>
|
||||
|
||||
<TagsEditor {doc} />
|
||||
|
||||
<CardAttributeEditor value={doc} {mixins} {readonly} ignoreKeys={['title', 'content', 'parent']} />
|
||||
|
||||
<Content {doc} {readonly} bind:content />
|
||||
</div>
|
||||
|
||||
<ComponentExtensions
|
||||
extension={card.extensions.EditCardExtension}
|
||||
props={{
|
||||
card: doc
|
||||
}}
|
||||
/>
|
||||
|
||||
<Childs object={doc} {readonly} />
|
||||
<RelationsEditor object={doc} {readonly} />
|
||||
|
||||
<Attachments objectId={doc._id} _class={doc._class} space={doc.space} attachments={doc.attachments ?? 0} />
|
||||
|
||||
<svelte:fragment slot="utils">
|
||||
{#if !readonly}
|
||||
<Button
|
||||
icon={IconMoreH}
|
||||
iconProps={{ size: 'medium' }}
|
||||
kind={'icon'}
|
||||
dataId={'btnMoreActions'}
|
||||
on:click={(e) => {
|
||||
showMenu(e, { object: doc, excludedActions: [view.action.Open] })
|
||||
}}
|
||||
/>
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
</Panel>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
.container {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
margin: auto;
|
||||
}
|
||||
.title {
|
||||
font-size: 2.25rem;
|
||||
margin-top: 1.75rem;
|
||||
margin-bottom: 1rem;
|
||||
}
|
||||
</style>
|
||||
@@ -0,0 +1,287 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 card, { Card, CardSection, CardViewDefaults } from '@hcengineering/card'
|
||||
import { Component, Loading, Scroller } from '@hcengineering/ui'
|
||||
import { getClient } from '@hcengineering/presentation'
|
||||
import { NotificationContext } from '@hcengineering/communication-types'
|
||||
import { MessageInput } from '@hcengineering/ui-next'
|
||||
import { Ref } from '@hcengineering/core'
|
||||
import { SvelteComponent } from 'svelte'
|
||||
import { TableOfContents } from '@hcengineering/text-editor-resources'
|
||||
import { Heading } from '@hcengineering/text-editor'
|
||||
|
||||
import { CardSectionAction } from '../types'
|
||||
|
||||
export let doc: Card
|
||||
export let context: NotificationContext | undefined = undefined
|
||||
export let isContextLoaded: boolean = false
|
||||
export let readonly: boolean = false
|
||||
|
||||
const client = getClient()
|
||||
|
||||
const sections: CardSection[] = client.getModel().findAllSync(card.class.CardSection, {})
|
||||
|
||||
let defaults: CardViewDefaults | undefined = undefined
|
||||
$: defaults = client.getHierarchy().classHierarchyMixin(doc._class, card.mixin.CardViewDefaults)
|
||||
|
||||
let selectedToc: Heading | undefined = undefined
|
||||
|
||||
const sectionElement: Record<Ref<CardSection>, HTMLElement | undefined> = {}
|
||||
const sectionRef: Record<Ref<CardSection>, SvelteComponent | undefined> = {}
|
||||
const sectionLoaded: Record<Ref<CardSection>, boolean | undefined> = {}
|
||||
let sectionOverlays: Record<Ref<CardSection>, boolean> = {}
|
||||
|
||||
let toc: Heading[] = []
|
||||
let subTocBySection: Record<string, Heading[]> = {}
|
||||
|
||||
let scrollDiv: HTMLDivElement | undefined | null = undefined
|
||||
let isScrollInitialized = false
|
||||
|
||||
let showOverlay = false
|
||||
|
||||
function onNavigationClick (heading: Heading): void {
|
||||
selectedToc = heading
|
||||
navigate()
|
||||
}
|
||||
|
||||
function navigate (): void {
|
||||
if (selectedToc === undefined) return
|
||||
const sectionId = selectedToc.group as Ref<CardSection>
|
||||
|
||||
const ref = sectionRef[sectionId]
|
||||
const isInnerNavigation = selectedToc.id !== sectionId
|
||||
if (ref?.navigate && isInnerNavigation) {
|
||||
ref.navigate(selectedToc.id)
|
||||
} else {
|
||||
sectionElement[sectionId]?.scrollIntoView()
|
||||
}
|
||||
isScrollInitialized = true
|
||||
}
|
||||
|
||||
function handleSectionLoaded (_id: Ref<CardSection>): void {
|
||||
const wasLoaded = sectionLoaded[_id] === true
|
||||
sectionLoaded[_id] = true
|
||||
if (!wasLoaded && selectedToc?.group === _id) {
|
||||
navigate()
|
||||
}
|
||||
}
|
||||
|
||||
function handleChangeNavigation (section: Ref<CardSection>, id: string): void {
|
||||
if (selectedToc?.group !== section) return
|
||||
selectedToc = toc.find((it) => it.group === section && it.id === id)
|
||||
}
|
||||
|
||||
function handleAction (section: Ref<CardSection>, action: CardSectionAction): void {
|
||||
if (action.id === 'toc') {
|
||||
subTocBySection[section] = action.toc
|
||||
subTocBySection = subTocBySection
|
||||
}
|
||||
|
||||
if (action.id === 'overlay') {
|
||||
sectionOverlays[section] = action.show
|
||||
sectionOverlays = sectionOverlays
|
||||
}
|
||||
}
|
||||
|
||||
function updateToc (sections: CardSection[], tocBySection: Record<string, Heading[]>): void {
|
||||
const newToc: Heading[] = []
|
||||
|
||||
for (const section of sections) {
|
||||
const subToc = tocBySection[section._id]
|
||||
if (section.navigation.length > 0) {
|
||||
newToc.push(
|
||||
...section.navigation.map((nav) => ({
|
||||
id: nav.id,
|
||||
titleIntl: nav.label,
|
||||
level: 0,
|
||||
group: section._id
|
||||
}))
|
||||
)
|
||||
} else {
|
||||
newToc.push({
|
||||
id: section._id,
|
||||
titleIntl: section.label,
|
||||
level: 0,
|
||||
group: section._id
|
||||
})
|
||||
}
|
||||
|
||||
if (subToc !== undefined) {
|
||||
newToc.push(...subToc.map((it) => ({ ...it, group: section._id })))
|
||||
}
|
||||
}
|
||||
|
||||
toc = newToc
|
||||
if (selectedToc == null || newToc.findIndex((it) => it.id === selectedToc?.id) === -1) {
|
||||
selectedToc =
|
||||
newToc.find(
|
||||
(it) =>
|
||||
it.group === defaults?.defaultSection &&
|
||||
(defaults?.defaultNavigation === undefined || it.id === defaults?.defaultNavigation)
|
||||
) ?? newToc[0]
|
||||
isScrollInitialized = isScrollInitialized ?? selectedToc.id === newToc[0].id
|
||||
}
|
||||
}
|
||||
|
||||
function onMessageSent (): void {
|
||||
if (scrollDiv == null) return
|
||||
const lastTocItem = toc[toc.length - 1]
|
||||
if (lastTocItem === undefined) return
|
||||
|
||||
if (selectedToc?.group === lastTocItem.group && selectedToc?.id === lastTocItem.id) {
|
||||
scrollDiv?.scroll({ top: scrollDiv.scrollHeight, behavior: 'instant' })
|
||||
} else {
|
||||
selectedToc = lastTocItem
|
||||
navigate()
|
||||
}
|
||||
}
|
||||
|
||||
function handleScroll (): void {
|
||||
if (scrollDiv == null || showOverlay) return
|
||||
const allLoaded = sections.every(({ _id }) => sectionLoaded[_id] === true)
|
||||
if (!allLoaded) return
|
||||
const scrollTop = scrollDiv.scrollTop ?? 0
|
||||
const offsets: Array<{ _id: Ref<CardSection>, offsetTop: number }> = []
|
||||
sections.forEach(({ _id }) => {
|
||||
const sectionRef = sectionElement[_id]
|
||||
if (sectionRef != null && scrollDiv != null) {
|
||||
offsets.push({ _id, offsetTop: sectionRef.offsetTop })
|
||||
}
|
||||
})
|
||||
offsets.sort((a, b) => a.offsetTop - b.offsetTop)
|
||||
|
||||
const selectedSectionId = offsets.filter((it) => it.offsetTop <= scrollTop + 50).pop()?._id
|
||||
|
||||
if (selectedSectionId != null && selectedSectionId !== selectedToc?.group) {
|
||||
selectedToc = toc.find((it) => it.group === selectedSectionId)
|
||||
}
|
||||
}
|
||||
|
||||
$: updateToc(sections, subTocBySection)
|
||||
$: showOverlay = !isScrollInitialized || Object.values(sectionOverlays).some((it) => it)
|
||||
</script>
|
||||
|
||||
{#if showOverlay}
|
||||
<div class="overlay">
|
||||
<Loading />
|
||||
</div>
|
||||
{/if}
|
||||
<div class="hulyComponent-content__container columns">
|
||||
<div class="hulyComponent-content__column content">
|
||||
<div class="toc-container">
|
||||
<div class="toc">
|
||||
<TableOfContents
|
||||
items={toc}
|
||||
selected={toc.find((it) => it.id === selectedToc?.id)}
|
||||
on:select={(evt) => {
|
||||
onNavigationClick(evt.detail)
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<Scroller
|
||||
padding="0"
|
||||
bottomPadding="var(--spacing-3)"
|
||||
disablePointerEventsOnScroll
|
||||
bind:divScroll={scrollDiv}
|
||||
onScroll={handleScroll}
|
||||
>
|
||||
<div class="hulyComponent-content gap withoutMaxWidth">
|
||||
{#each sections as section, i}
|
||||
{@const isLoadingBefore = sections.slice(0, i).some((section) => sectionLoaded[section._id] === undefined)}
|
||||
<div id={section._id} bind:this={sectionElement[section._id]} class="section">
|
||||
<Component
|
||||
is={section.component}
|
||||
bind:innerRef={sectionRef[section._id]}
|
||||
showLoading={false}
|
||||
props={{
|
||||
doc,
|
||||
readonly,
|
||||
isContextLoaded,
|
||||
isLoadingBefore,
|
||||
scrollDiv,
|
||||
notificationContext: context,
|
||||
contentDiv: sectionElement[section._id],
|
||||
active: selectedToc?.group === section._id,
|
||||
navigation: selectedToc?.id
|
||||
}}
|
||||
on:loaded={() => {
|
||||
handleSectionLoaded(section._id)
|
||||
}}
|
||||
on:change={(ev) => {
|
||||
handleChangeNavigation(section._id, ev.detail)
|
||||
}}
|
||||
on:action={(ev) => {
|
||||
handleAction(section._id, ev.detail)
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
</Scroller>
|
||||
|
||||
{#if !readonly}
|
||||
<div class="message-input">
|
||||
<MessageInput cardId={doc._id} cardType={doc._class} title={doc.title} on:sent={onMessageSent} />
|
||||
</div>
|
||||
{/if}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.message-input {
|
||||
display: flex;
|
||||
width: 100%;
|
||||
flex-direction: column;
|
||||
align-items: flex-start;
|
||||
padding: 0 0.75rem;
|
||||
min-height: 8.5rem;
|
||||
max-height: 50%;
|
||||
}
|
||||
.overlay {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: absolute;
|
||||
z-index: 1;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
background-color: var(--theme-panel-color);
|
||||
}
|
||||
|
||||
.toc-container {
|
||||
position: absolute;
|
||||
pointer-events: none;
|
||||
inset: 0;
|
||||
z-index: 1;
|
||||
top: 0;
|
||||
left: 0.5rem;
|
||||
}
|
||||
|
||||
.toc {
|
||||
width: 2rem;
|
||||
pointer-events: all;
|
||||
position: sticky;
|
||||
}
|
||||
|
||||
.section {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: flex-start;
|
||||
align-self: stretch;
|
||||
}
|
||||
</style>
|
||||
@@ -53,7 +53,7 @@
|
||||
|
||||
const filter = (it: Doc): boolean => {
|
||||
const card = it as Card
|
||||
return !card.parentInfo.some((p) => cards.has(p._id))
|
||||
return !card.parentInfo?.some((p) => cards.has(p._id))
|
||||
}
|
||||
</script>
|
||||
|
||||
|
||||
@@ -0,0 +1,51 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { Attachments } from '@hcengineering/attachment-resources'
|
||||
import { createEventDispatcher, onMount } from 'svelte'
|
||||
|
||||
export let readonly: boolean = false
|
||||
export let doc: Card
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
onMount(() => {
|
||||
if ((doc.attachments ?? 0) === 0) {
|
||||
dispatch('loaded')
|
||||
}
|
||||
})
|
||||
</script>
|
||||
|
||||
<div class="section-attachments">
|
||||
<Attachments
|
||||
objectId={doc._id}
|
||||
_class={doc._class}
|
||||
space={doc.space}
|
||||
attachments={doc.attachments ?? 0}
|
||||
{readonly}
|
||||
on:attachments={() => dispatch('loaded')}
|
||||
/>
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.section-attachments {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
padding: 0 4rem;
|
||||
}
|
||||
</style>
|
||||
@@ -0,0 +1,45 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { onMount, createEventDispatcher } from 'svelte'
|
||||
|
||||
import Childs from '../Childs.svelte'
|
||||
|
||||
export let readonly: boolean = false
|
||||
export let doc: Card
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
onMount(() => {
|
||||
if ((doc.children ?? 0) === 0) {
|
||||
dispatch('loaded')
|
||||
}
|
||||
})
|
||||
</script>
|
||||
|
||||
<div class="section-children">
|
||||
<Childs object={doc} {readonly} on:docs={() => dispatch('loaded')} />
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.section-children {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
padding: 0 4rem;
|
||||
}
|
||||
</style>
|
||||
@@ -0,0 +1,60 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { Heading } from '@hcengineering/text-editor'
|
||||
import { createEventDispatcher, onMount } from 'svelte'
|
||||
|
||||
import Content from '../Content.svelte'
|
||||
import { CardSectionAction } from '../../types'
|
||||
|
||||
export let readonly: boolean = false
|
||||
export let doc: Card
|
||||
export let contentDiv: HTMLDivElement | undefined | null = undefined
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
export function navigate (id: string): void {
|
||||
const element = window.document.getElementById(id)
|
||||
element?.scrollIntoView({ behavior: 'instant', block: 'start' })
|
||||
}
|
||||
|
||||
function handleHeadings (ev: CustomEvent<Heading[]>): void {
|
||||
const headings = ev.detail
|
||||
const action: CardSectionAction = { id: 'toc', toc: headings }
|
||||
dispatch('action', action)
|
||||
}
|
||||
|
||||
onMount(() => {
|
||||
dispatch('action', { id: 'toc', toc: [] })
|
||||
})
|
||||
</script>
|
||||
|
||||
{#if contentDiv != null}
|
||||
<div class="content">
|
||||
<Content {doc} {readonly} content={contentDiv} showToc={false} on:loaded on:headings={handleHeadings} />
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
.content {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
padding: 0 5rem;
|
||||
flex: 1;
|
||||
}
|
||||
</style>
|
||||
@@ -0,0 +1,47 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { Doc, Mixin } from '@hcengineering/core'
|
||||
import { getDocMixins } from '@hcengineering/view-resources'
|
||||
import { createEventDispatcher, onMount } from 'svelte'
|
||||
|
||||
import CardAttributeEditor from '../CardAttributeEditor.svelte'
|
||||
|
||||
export let readonly: boolean = false
|
||||
export let doc: Card
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
let mixins: Array<Mixin<Doc>> = []
|
||||
$: mixins = getDocMixins(doc)
|
||||
onMount(() => {
|
||||
dispatch('loaded')
|
||||
})
|
||||
</script>
|
||||
|
||||
<div class="properties">
|
||||
<CardAttributeEditor value={doc} {mixins} {readonly} ignoreKeys={['title', 'content', 'parent']} />
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.properties {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
padding: 0 4rem;
|
||||
}
|
||||
</style>
|
||||
+15
-12
@@ -14,19 +14,22 @@
|
||||
-->
|
||||
|
||||
<script lang="ts">
|
||||
import { MessageInput, UploadedFile } from '@hcengineering/ui-next'
|
||||
import { Card } from '@hcengineering/card'
|
||||
import { RelationsEditor } from '@hcengineering/view-resources'
|
||||
|
||||
import chat from '../plugin'
|
||||
|
||||
export let card: Card | undefined
|
||||
export let onSubmit: ((markdown: string, files: UploadedFile[]) => Promise<void>) | undefined = undefined
|
||||
export let readonly: boolean = false
|
||||
export let doc: Card
|
||||
</script>
|
||||
|
||||
<MessageInput
|
||||
cardId={card?._id}
|
||||
cardType={card?._class}
|
||||
placeholder={chat.string.MessageIn}
|
||||
placeholderParams={{ title: card?.title ?? '' }}
|
||||
{onSubmit}
|
||||
/>
|
||||
<div class="section-relations">
|
||||
<RelationsEditor object={doc} {readonly} on:loaded />
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.section-relations {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
padding: 0 4rem;
|
||||
}
|
||||
</style>
|
||||
@@ -49,6 +49,14 @@ import SpacePresenter from './components/navigator/SpacePresenter.svelte'
|
||||
import LabelsPresenter from './components/LabelsPresenter.svelte'
|
||||
import RolesSection from './components/settings/RolesSection.svelte'
|
||||
import EditRole from './components/settings/EditRole.svelte'
|
||||
import CardWidget from './components/CardWidget.svelte'
|
||||
|
||||
// Card Sections
|
||||
import AttachmentsCardSection from './components/sections/AttachmentsSection.svelte'
|
||||
import ChildrenCardSection from './components/sections/ChildrenSection.svelte'
|
||||
import ContentCardSection from './components/sections/ContentSection.svelte'
|
||||
import PropertiesCardSection from './components/sections/PropertiesSection.svelte'
|
||||
import RelationsCardSection from './components/sections/RelationsSection.svelte'
|
||||
|
||||
export { default as CardSelector } from './components/CardSelector.svelte'
|
||||
export { default as Navigator } from './components/navigator-next/Navigator.svelte'
|
||||
@@ -83,7 +91,15 @@ export default async (): Promise<Resources> => ({
|
||||
SpacePresenter,
|
||||
LabelsPresenter,
|
||||
RolesSection,
|
||||
EditRole
|
||||
EditRole,
|
||||
CardWidget
|
||||
},
|
||||
sectionComponent: {
|
||||
AttachmentsSection: AttachmentsCardSection,
|
||||
ChildrenSection: ChildrenCardSection,
|
||||
ContentSection: ContentCardSection,
|
||||
PropertiesSection: PropertiesCardSection,
|
||||
RelationsSection: RelationsCardSection
|
||||
},
|
||||
completion: {
|
||||
CardQuery: queryCard
|
||||
|
||||
@@ -48,7 +48,15 @@ export default mergeIds(cardId, card, {
|
||||
SpacePresenter: '' as AnyComponent,
|
||||
LabelsPresenter: '' as AnyComponent,
|
||||
RolesSection: '' as AnyComponent,
|
||||
EditRole: '' as AnyComponent
|
||||
EditRole: '' as AnyComponent,
|
||||
CardWidget: '' as AnyComponent
|
||||
},
|
||||
sectionComponent: {
|
||||
AttachmentsSection: '' as AnyComponent,
|
||||
ChildrenSection: '' as AnyComponent,
|
||||
ContentSection: '' as AnyComponent,
|
||||
PropertiesSection: '' as AnyComponent,
|
||||
RelationsSection: '' as AnyComponent
|
||||
},
|
||||
completion: {
|
||||
CardQuery: '' as Resource<ObjectSearchFactory>,
|
||||
@@ -90,6 +98,7 @@ export default mergeIds(cardId, card, {
|
||||
SelectType: '' as IntlString,
|
||||
CreateSpace: '' as IntlString,
|
||||
NumberTypes: '' as IntlString,
|
||||
Labels: '' as IntlString
|
||||
Labels: '' as IntlString,
|
||||
Properties: '' as IntlString
|
||||
}
|
||||
})
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
import type { Ref } from '@hcengineering/core'
|
||||
import type { MasterTag } from '@hcengineering/card'
|
||||
import type { LabelID } from '@hcengineering/communication-types'
|
||||
import { type Heading } from '@hcengineering/text-editor'
|
||||
|
||||
interface BaseNavigatorConfig {
|
||||
types: Array<Ref<MasterTag>>
|
||||
@@ -37,3 +38,15 @@ export interface CardsNavigatorConfig extends BaseNavigatorConfig {
|
||||
}
|
||||
|
||||
export type NavigatorConfig = TypesNavigatorConfig | CardsNavigatorConfig
|
||||
|
||||
export interface CardTocAction {
|
||||
id: 'toc'
|
||||
toc: Heading[]
|
||||
}
|
||||
|
||||
export interface CardOverlayAction {
|
||||
id: 'overlay'
|
||||
show: boolean
|
||||
}
|
||||
|
||||
export type CardSectionAction = CardTocAction | CardOverlayAction
|
||||
|
||||
@@ -11,7 +11,7 @@
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
import { type Card, CardEvents, cardId, type CardSpace, type MasterTag } from '@hcengineering/card'
|
||||
import { type Card, CardEvents, cardId, type CardSpace, type CardSection, type MasterTag } from '@hcengineering/card'
|
||||
import {
|
||||
type Class,
|
||||
type Client,
|
||||
@@ -38,10 +38,11 @@ import {
|
||||
} from '@hcengineering/ui'
|
||||
import view from '@hcengineering/view'
|
||||
import { accessDeniedStore } from '@hcengineering/view-resources'
|
||||
import { type LocationData } from '@hcengineering/workbench'
|
||||
import workbench, { type LocationData } from '@hcengineering/workbench'
|
||||
import { translate } from '@hcengineering/platform'
|
||||
import { makeRank } from '@hcengineering/rank'
|
||||
import { Analytics } from '@hcengineering/analytics'
|
||||
import { openWidget } from '@hcengineering/workbench-resources'
|
||||
|
||||
import CardSearchItem from './components/CardSearchItem.svelte'
|
||||
import CreateSpace from './components/navigator/CreateSpace.svelte'
|
||||
@@ -227,3 +228,27 @@ export function sortNavigatorTypes (types: MasterTag[], config: NavigatorConfig)
|
||||
return a.label.localeCompare(b.label)
|
||||
})
|
||||
}
|
||||
|
||||
export interface CardWidgetData {
|
||||
_id: Ref<Card>
|
||||
name: string
|
||||
tab?: Ref<CardSection>
|
||||
}
|
||||
|
||||
export async function openCardInSidebar (cardId: Ref<Card>, doc?: Card, tabId?: Ref<CardSection>): Promise<void> {
|
||||
const client = getClient()
|
||||
|
||||
const widget = client.getModel().findAllSync(workbench.class.Widget, { _id: card.ids.CardWidget as any })[0]
|
||||
if (widget === undefined) return
|
||||
|
||||
const object = doc ?? (await client.findOne(card.class.Card, { _id: cardId }))
|
||||
if (object === undefined) return
|
||||
|
||||
const data: CardWidgetData = {
|
||||
_id: cardId,
|
||||
name: object.title,
|
||||
tab: tabId
|
||||
}
|
||||
|
||||
openWidget(widget, data)
|
||||
}
|
||||
|
||||
@@ -71,6 +71,23 @@ export interface MasterTagEditorSection extends Doc {
|
||||
masterOnly?: boolean
|
||||
}
|
||||
|
||||
export interface CardNavigation {
|
||||
id: string
|
||||
label: IntlString
|
||||
}
|
||||
|
||||
export interface CardSection extends Doc {
|
||||
label: IntlString
|
||||
component: AnyComponent
|
||||
order: number
|
||||
navigation: CardNavigation[]
|
||||
}
|
||||
|
||||
export interface CardViewDefaults extends MasterTag {
|
||||
defaultSection: Ref<CardSection>
|
||||
defaultNavigation?: string
|
||||
}
|
||||
|
||||
/**
|
||||
* @public
|
||||
*/
|
||||
@@ -88,7 +105,11 @@ const cardPlugin = plugin(cardId, {
|
||||
Tag: '' as Ref<Class<Tag>>,
|
||||
MasterTagEditorSection: '' as Ref<Class<MasterTagEditorSection>>,
|
||||
CardSpace: '' as Ref<Class<CardSpace>>,
|
||||
Role: '' as Ref<Class<Role>>
|
||||
Role: '' as Ref<Class<Role>>,
|
||||
CardSection: '' as Ref<Class<CardSection>>
|
||||
},
|
||||
mixin: {
|
||||
CardViewDefaults: '' as Ref<Mixin<CardViewDefaults>>
|
||||
},
|
||||
space: {
|
||||
Default: '' as Ref<CardSpace>
|
||||
@@ -119,6 +140,16 @@ const cardPlugin = plugin(cardId, {
|
||||
Cards: '' as IntlString,
|
||||
CardApplication: '' as IntlString,
|
||||
Views: '' as IntlString
|
||||
},
|
||||
section: {
|
||||
Attachments: '' as Ref<CardSection>,
|
||||
Children: '' as Ref<CardSection>,
|
||||
Content: '' as Ref<CardSection>,
|
||||
Properties: '' as Ref<CardSection>,
|
||||
Relations: '' as Ref<CardSection>
|
||||
},
|
||||
ids: {
|
||||
CardWidget: '' as Ref<Doc>
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
@@ -42,7 +42,7 @@
|
||||
"@hcengineering/card": "^0.6.0",
|
||||
"@hcengineering/card-resources": "^0.6.0",
|
||||
"@hcengineering/chat": "^0.6.0",
|
||||
"@hcengineering/communication-types": "0.1.172",
|
||||
"@hcengineering/communication-types": "0.1.174",
|
||||
"@hcengineering/contact": "^0.6.24",
|
||||
"@hcengineering/contact-resources": "^0.6.0",
|
||||
"@hcengineering/core": "^0.6.32",
|
||||
|
||||
@@ -21,21 +21,27 @@
|
||||
deviceOptionsStore as deviceInfo,
|
||||
resolvedLocationStore,
|
||||
Location,
|
||||
restoreLocation
|
||||
restoreLocation,
|
||||
Component
|
||||
} from '@hcengineering/ui'
|
||||
import { onDestroy } from 'svelte'
|
||||
import { getClient } from '@hcengineering/presentation'
|
||||
import { chatId } from '@hcengineering/chat'
|
||||
import { Ref } from '@hcengineering/core'
|
||||
import { Ref, Doc, Class } from '@hcengineering/core'
|
||||
import view from '@hcengineering/view'
|
||||
|
||||
import ChatPanel from './ChatPanel.svelte'
|
||||
import ChatNavigation from './ChatNavigation.svelte'
|
||||
import { navigateToCard, getCardIdFromLocation, navigateToType, getTypeIdFromLocation } from '../location'
|
||||
import ChatNavigationCategoryList from './ChatNavigationCategoryList.svelte'
|
||||
|
||||
type Selection = { type: 'card', card: Card } | { type: 'type', ref: Ref<MasterTag> }
|
||||
interface Selection {
|
||||
_class: Ref<Class<Doc>>
|
||||
_id: Ref<Doc>
|
||||
doc: Doc
|
||||
}
|
||||
|
||||
const client = getClient()
|
||||
const hierarchy = client.getHierarchy()
|
||||
|
||||
let replacedPanelElement: HTMLElement
|
||||
let selection: Selection | undefined = undefined
|
||||
@@ -50,9 +56,10 @@
|
||||
}
|
||||
|
||||
const typeId = getTypeIdFromLocation(loc)
|
||||
const type = typeId != null ? await client.findOne(cardPlugin.class.MasterTag, { _id: typeId }) : undefined
|
||||
|
||||
if (typeId != null && typeId !== '') {
|
||||
selection = { type: 'type', ref: typeId }
|
||||
if (type != null) {
|
||||
selection = { _class: cardPlugin.class.MasterTag, _id: type._id, doc: type }
|
||||
return
|
||||
}
|
||||
|
||||
@@ -71,33 +78,34 @@
|
||||
|
||||
if (cardId !== selectedCard?._id) {
|
||||
const card = await client.findOne(cardPlugin.class.Card, { _id: cardId })
|
||||
selection = card != null ? { type: 'card', card } : undefined
|
||||
selection = card != null ? { _class: cardPlugin.class.Card, _id: cardId, doc: card } : undefined
|
||||
}
|
||||
}
|
||||
|
||||
function selectCard (event: CustomEvent<Card>): void {
|
||||
if (selection?._id === event.detail._id) return
|
||||
const card = event.detail
|
||||
selection = { type: 'card', card }
|
||||
selection = { _class: cardPlugin.class.Card, _id: card._id, doc: card }
|
||||
navigateToCard(card._id)
|
||||
}
|
||||
|
||||
function selectType (event: CustomEvent<MasterTag>): void {
|
||||
if (selection && selection.type === 'type' && selection.ref === event.detail._id) return
|
||||
if (selection?._id === event.detail._id) return
|
||||
const type = event.detail
|
||||
selection = { type: 'type', ref: type._id }
|
||||
selection = { _class: cardPlugin.class.MasterTag, _id: type._id, doc: type }
|
||||
navigateToType(type._id)
|
||||
}
|
||||
|
||||
function getSelectedCard (selection: Selection | undefined): Card | undefined {
|
||||
if (selection == null) return undefined
|
||||
if (selection.type !== 'card') return undefined
|
||||
return selection.card
|
||||
if (selection._class !== cardPlugin.class.Card) return undefined
|
||||
return selection.doc as Card | undefined
|
||||
}
|
||||
|
||||
function getSelectedType (selection: Selection | undefined): Ref<MasterTag> | undefined {
|
||||
if (selection == null) return undefined
|
||||
if (selection.type !== 'type') return undefined
|
||||
return selection.ref
|
||||
if (selection._class !== cardPlugin.class.MasterTag) return undefined
|
||||
return selection._id as Ref<MasterTag>
|
||||
}
|
||||
|
||||
onDestroy(
|
||||
@@ -146,7 +154,9 @@
|
||||
{/if}
|
||||
<div bind:this={replacedPanelElement} class="hulyComponent chat__panel">
|
||||
{#if selectedCard}
|
||||
<ChatPanel card={selectedCard} />
|
||||
{@const panelComponent = hierarchy.classHierarchyMixin(selectedCard._class, view.mixin.ObjectPanel)}
|
||||
{@const comp = panelComponent?.component ?? view.component.EditDoc}
|
||||
<Component is={comp} props={{ _id: selectedCard._id, readonly: false, embedded: true, allowClose: false }} />
|
||||
{:else if selectedType}
|
||||
<ChatNavigationCategoryList type={selectedType} />
|
||||
{/if}
|
||||
@@ -155,18 +165,18 @@
|
||||
|
||||
<style lang="scss">
|
||||
.chat {
|
||||
background: var(--next-background-color);
|
||||
border-color: var(--next-border-color);
|
||||
background: var(--theme-navpanel-color);
|
||||
border-color: var(--theme-divider-color);
|
||||
}
|
||||
|
||||
.chat__navigator {
|
||||
background: var(--next-background-color);
|
||||
border-color: var(--next-border-color);
|
||||
background: var(--theme-navpanel-color);
|
||||
border-color: var(--theme-divider-color);
|
||||
}
|
||||
|
||||
.chat__panel {
|
||||
background: var(--next-panel-color-background);
|
||||
border-color: var(--next-panel-color-border);
|
||||
background: var(--theme-panel-color);
|
||||
border-color: var(--theme-divider-color);
|
||||
position: relative;
|
||||
}
|
||||
</style>
|
||||
|
||||
@@ -1,331 +0,0 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { type Message, Window, NotificationContext } from '@hcengineering/communication-types'
|
||||
import { createMessagesQuery, getCommunicationClient } from '@hcengineering/presentation'
|
||||
import { MessagesGroup as MessagesGroupPresenter } from '@hcengineering/ui-next'
|
||||
import { Scroller } from '@hcengineering/ui'
|
||||
import { getCurrentAccount, SortingOrder } from '@hcengineering/core'
|
||||
import { tick, onDestroy } from 'svelte'
|
||||
|
||||
import ReverseScroller from './internal/ReverseScroller.svelte'
|
||||
import { createMessagesObserver, getGroupDay, groupMessagesByDay, MessagesGroup } from '../ui'
|
||||
import { replyToThread } from '../actions'
|
||||
import ChatLoadingFiller from './ChatLoadingFiller.svelte'
|
||||
|
||||
export let card: Card | undefined = undefined
|
||||
export let context: NotificationContext | undefined = undefined
|
||||
export let bottomStart: boolean = true
|
||||
export let footerHeight: number | undefined = undefined
|
||||
export let showDates: boolean = true
|
||||
export let overlyColor: string | undefined = undefined
|
||||
|
||||
const me = getCurrentAccount()
|
||||
const communicationClient = getCommunicationClient()
|
||||
const query = createMessagesQuery()
|
||||
|
||||
const loadPageThreshold = 200
|
||||
const scrollToNewThreshold = 50
|
||||
|
||||
const initialLastView = context?.lastView
|
||||
const initialLastUpdate = context?.lastUpdate
|
||||
|
||||
let contentDiv: HTMLDivElement | null | undefined = undefined
|
||||
let scrollDiv: HTMLDivElement | null | undefined = undefined
|
||||
let scroller: Scroller | undefined | null = undefined
|
||||
|
||||
let separatorDiv: HTMLDivElement | null | undefined = undefined
|
||||
|
||||
let messages: Message[] = []
|
||||
let groups: MessagesGroup[] = []
|
||||
let window: Window<Message> | undefined = undefined
|
||||
let isLoading = true
|
||||
let messagesCount = 0
|
||||
|
||||
let isScrollInitialized = false
|
||||
let isPageLoading = false
|
||||
let shouldScrollToNew = true
|
||||
let restore: { scrollTop: number, scrollHeight: number } | undefined = undefined
|
||||
|
||||
$: if (card != null) {
|
||||
const limit = 50
|
||||
const unread = initialLastView != null && initialLastUpdate != null && initialLastUpdate > initialLastView
|
||||
const order = unread ? SortingOrder.Ascending : SortingOrder.Descending
|
||||
query.query(
|
||||
{
|
||||
card: card._id,
|
||||
replies: true,
|
||||
files: true,
|
||||
reactions: true,
|
||||
order,
|
||||
limit,
|
||||
created:
|
||||
unread && initialLastView != null
|
||||
? {
|
||||
greaterOrEqual: initialLastView
|
||||
}
|
||||
: undefined
|
||||
},
|
||||
(res: Window<Message>) => {
|
||||
window = res
|
||||
messages = order === SortingOrder.Ascending ? res.getResult() : res.getResult().reverse()
|
||||
if (messages.length < limit && res.hasNextPage()) {
|
||||
void window.loadNextPage()
|
||||
} else if (messages.length < limit && res.hasPrevPage()) {
|
||||
void window.loadPrevPage()
|
||||
}
|
||||
groups = groupMessagesByDay(messages)
|
||||
isLoading = messages.length < limit && (res.hasNextPage() || res.hasPrevPage())
|
||||
void onUpdate(messages)
|
||||
}
|
||||
)
|
||||
} else {
|
||||
isLoading = true
|
||||
window = undefined
|
||||
groups = []
|
||||
query.unsubscribe()
|
||||
}
|
||||
|
||||
function updateShouldScrollToNew (): void {
|
||||
if (scrollDiv != null && contentDiv != null) {
|
||||
const { scrollTop } = scrollDiv
|
||||
|
||||
shouldScrollToNew = Math.abs(scrollTop) < scrollToNewThreshold
|
||||
}
|
||||
}
|
||||
|
||||
function shouldLoadPrevPage (): boolean {
|
||||
if (scrollDiv == null) return false
|
||||
const { scrollHeight, scrollTop, clientHeight } = scrollDiv
|
||||
|
||||
return scrollHeight + Math.ceil(scrollTop - clientHeight) <= loadPageThreshold
|
||||
}
|
||||
|
||||
function shouldLoadNextPage (): boolean {
|
||||
if (scrollDiv == null) return false
|
||||
|
||||
return Math.abs(scrollDiv.scrollTop) <= loadPageThreshold
|
||||
}
|
||||
|
||||
function loadMore (): void {
|
||||
if (window === undefined) return
|
||||
|
||||
if (shouldLoadPrevPage() && window.hasPrevPage()) {
|
||||
void loadPrevPage()
|
||||
} else if (shouldLoadNextPage() && window.hasNextPage()) {
|
||||
void loadNextPage()
|
||||
}
|
||||
}
|
||||
|
||||
async function loadPrevPage (): Promise<void> {
|
||||
if (window === undefined || isPageLoading || scrollDiv == null) return
|
||||
if ((restore?.scrollTop ?? 0) !== 0) return
|
||||
|
||||
try {
|
||||
isPageLoading = true
|
||||
shouldScrollToNew = false
|
||||
await window.loadPrevPage()
|
||||
restore = {
|
||||
scrollTop: scrollDiv?.scrollTop ?? 0,
|
||||
scrollHeight: 0
|
||||
}
|
||||
} finally {
|
||||
isPageLoading = false
|
||||
}
|
||||
}
|
||||
|
||||
async function loadNextPage (): Promise<void> {
|
||||
if (window === undefined || isPageLoading || scrollDiv == null) return
|
||||
|
||||
if ((restore?.scrollHeight ?? 0) !== 0) return
|
||||
|
||||
try {
|
||||
isPageLoading = true
|
||||
shouldScrollToNew = false
|
||||
await window.loadNextPage()
|
||||
restore = {
|
||||
scrollTop: 0,
|
||||
scrollHeight: scrollDiv?.scrollHeight ?? 0
|
||||
}
|
||||
} finally {
|
||||
isPageLoading = false
|
||||
}
|
||||
}
|
||||
|
||||
function scrollToBottom (): void {
|
||||
if (scrollDiv != null) {
|
||||
scrollDiv.scroll({ top: 0, behavior: 'instant' })
|
||||
}
|
||||
}
|
||||
|
||||
function restoreScroll (): void {
|
||||
if (scrollDiv == null || scroller == null || restore == null) return
|
||||
if (restore.scrollTop !== 0) {
|
||||
scroller.scroll(restore.scrollTop)
|
||||
}
|
||||
if (restore.scrollHeight !== 0) {
|
||||
const delta = restore.scrollHeight - scrollDiv.scrollHeight
|
||||
scroller.scroll(delta)
|
||||
}
|
||||
restore = undefined
|
||||
}
|
||||
|
||||
function handleScroll (): void {
|
||||
loadMore()
|
||||
updateShouldScrollToNew()
|
||||
}
|
||||
|
||||
async function onUpdate (res: Message[]): Promise<void> {
|
||||
if (messagesCount === res.length) return
|
||||
const prevCount = messagesCount
|
||||
messagesCount = res.length
|
||||
|
||||
if (prevCount > messagesCount) return
|
||||
await tick()
|
||||
|
||||
restoreScroll()
|
||||
|
||||
if (shouldScrollToNew && prevCount > 0) {
|
||||
scrollToBottom()
|
||||
}
|
||||
}
|
||||
|
||||
let newLastView: Date | undefined = context?.lastView
|
||||
let separatorDate: Date | undefined = undefined
|
||||
let readMessagesTimer: any | undefined = undefined
|
||||
let unsubscribeObserver: (() => void) | undefined = undefined
|
||||
|
||||
function readMessage (date: Date): void {
|
||||
if (readMessagesTimer != null) {
|
||||
clearTimeout(readMessagesTimer)
|
||||
readMessagesTimer = undefined
|
||||
}
|
||||
readMessagesTimer = setTimeout(async () => {
|
||||
if (context == null || context.lastView >= date) return
|
||||
await communicationClient.updateNotificationContext(context.id, date)
|
||||
}, 500)
|
||||
}
|
||||
|
||||
$: initMessageObserver(contentDiv, isScrollInitialized, context)
|
||||
|
||||
function initMessageObserver (
|
||||
contentDiv: HTMLDivElement | undefined | null,
|
||||
isScrollInitialized: boolean,
|
||||
context: NotificationContext | undefined
|
||||
): void {
|
||||
if (contentDiv == null || !isScrollInitialized || context == null) return
|
||||
if (unsubscribeObserver != null) return
|
||||
|
||||
unsubscribeObserver = createMessagesObserver(contentDiv, (messageDiv) => {
|
||||
const id = messageDiv.id
|
||||
const message = messages.find((it) => it.id === id)
|
||||
|
||||
if (message === undefined) return
|
||||
const shouldRead = newLastView == null || message.created > newLastView
|
||||
|
||||
if (shouldRead) {
|
||||
newLastView = message.created
|
||||
readMessage(message.created)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
async function handleReply (event: CustomEvent<Message>): Promise<void> {
|
||||
if (card == null) return
|
||||
const message = event.detail
|
||||
await replyToThread(message, card)
|
||||
}
|
||||
|
||||
$: void initializeScroll(isLoading, separatorDiv)
|
||||
|
||||
async function initializeScroll (isLoading: boolean, separatorDiv?: HTMLDivElement | null): Promise<void> {
|
||||
if (isLoading || isScrollInitialized) return
|
||||
|
||||
const separatorIndex = initialLastView
|
||||
? messages.findIndex(({ created, creator }) => !me.socialIds.includes(creator) && created > initialLastView)
|
||||
: -1
|
||||
|
||||
if (separatorIndex === -1) {
|
||||
isScrollInitialized = true
|
||||
separatorDate = undefined
|
||||
return
|
||||
}
|
||||
|
||||
separatorDate = messages[separatorIndex].created
|
||||
if (separatorDiv != null) {
|
||||
await tick() // Wait for the DOM to update
|
||||
separatorDiv.scrollIntoView({ behavior: 'instant', block: 'start' })
|
||||
if (scrollDiv && scrollDiv.scrollTop < -100) {
|
||||
scroller?.scrollBy(-50)
|
||||
}
|
||||
isScrollInitialized = true
|
||||
updateShouldScrollToNew()
|
||||
}
|
||||
}
|
||||
|
||||
onDestroy(() => {
|
||||
if (unsubscribeObserver != null) {
|
||||
unsubscribeObserver()
|
||||
}
|
||||
})
|
||||
</script>
|
||||
|
||||
<ReverseScroller
|
||||
bind:scrollDiv
|
||||
bind:scroller
|
||||
bind:contentDiv
|
||||
{overlyColor}
|
||||
isLoading={card != null && (isLoading || !isScrollInitialized)}
|
||||
{bottomStart}
|
||||
onScroll={handleScroll}
|
||||
>
|
||||
{#if card}
|
||||
{#if window !== undefined && window.hasPrevPage()}
|
||||
<ChatLoadingFiller />
|
||||
{/if}
|
||||
{#each groups as group (group.day.toString())}
|
||||
{@const withSeparator = separatorDate != null && getGroupDay(separatorDate) === group.day}
|
||||
{#if withSeparator}
|
||||
<MessagesGroupPresenter
|
||||
bind:separatorDiv
|
||||
{card}
|
||||
date={group.day}
|
||||
messages={group.messages}
|
||||
{showDates}
|
||||
{separatorDate}
|
||||
on:reply={handleReply}
|
||||
/>
|
||||
{:else}
|
||||
<MessagesGroupPresenter {card} date={group.day} messages={group.messages} {showDates} on:reply={handleReply} />
|
||||
{/if}
|
||||
{/each}
|
||||
{#if window !== undefined && window.hasNextPage()}
|
||||
<ChatLoadingFiller />
|
||||
{/if}
|
||||
|
||||
{#if footerHeight != null && footerHeight > 0}
|
||||
<div class="filler" style:height={`${footerHeight}px`} />
|
||||
{/if}
|
||||
{/if}
|
||||
</ReverseScroller>
|
||||
|
||||
<style lang="scss">
|
||||
.filler {
|
||||
display: flex;
|
||||
width: 100%;
|
||||
}
|
||||
</style>
|
||||
@@ -1,55 +0,0 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { UploadedFile } from '@hcengineering/ui-next'
|
||||
|
||||
import ChatInput from './ChatInput.svelte'
|
||||
|
||||
export let card: Card | undefined = undefined
|
||||
export let height: number | undefined = undefined
|
||||
export let onSubmit: ((markdown: string, files: UploadedFile[]) => Promise<void>) | undefined = undefined
|
||||
|
||||
let _height: number | undefined | null
|
||||
|
||||
$: if (_height != null) {
|
||||
// Add 1 for the border
|
||||
height = _height + 1
|
||||
}
|
||||
</script>
|
||||
|
||||
<div class="chat__footer" bind:clientHeight={_height}>
|
||||
<ChatInput {card} {onSubmit} />
|
||||
</div>
|
||||
|
||||
<style lang="scss">
|
||||
.chat__footer {
|
||||
display: flex;
|
||||
width: 100%;
|
||||
flex-direction: column;
|
||||
align-items: flex-start;
|
||||
padding: 1.25rem 0.75rem;
|
||||
padding-bottom: 0;
|
||||
|
||||
border-top: 1px solid var(--next-divider-color);
|
||||
backdrop-filter: blur(5px);
|
||||
min-height: 100px;
|
||||
position: absolute;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
max-height: 50%;
|
||||
}
|
||||
</style>
|
||||
@@ -1,67 +0,0 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 cardPlugin, { Card } from '@hcengineering/card'
|
||||
import { Header, Icon } from '@hcengineering/ui'
|
||||
import { getClient } from '@hcengineering/presentation'
|
||||
import { Asset } from '@hcengineering/platform'
|
||||
import { PresenceAvatars } from '@hcengineering/presence-resources'
|
||||
|
||||
export let card: Card | undefined = undefined
|
||||
export let canClose: boolean = false
|
||||
export let title: string | undefined = undefined
|
||||
export let icon: Asset | undefined = undefined
|
||||
|
||||
const client = getClient()
|
||||
const hierarchy = client.getHierarchy()
|
||||
|
||||
$: clazz = card != null ? hierarchy.getClass(card._class) : undefined
|
||||
</script>
|
||||
|
||||
<Header
|
||||
allowFullsize={false}
|
||||
type={canClose ? 'type-aside' : 'type-component'}
|
||||
adaptive="disabled"
|
||||
hideBefore={false}
|
||||
closeOnEscape={false}
|
||||
on:close
|
||||
>
|
||||
<div class="hulyHeader-titleGroup">
|
||||
<div class="content-color mr-2 pl-2">
|
||||
<Icon icon={clazz?.icon ?? icon ?? cardPlugin.icon.Card} size={'small'} />
|
||||
</div>
|
||||
<span class="secondary-textColor overflow-label heading-medium-16 line-height-auto mr-2"
|
||||
>{card?.title ?? title}</span
|
||||
>
|
||||
</div>
|
||||
|
||||
<svelte:fragment slot="presence">
|
||||
{#if card}
|
||||
<PresenceAvatars object={card} size="x-small" limit={5} />
|
||||
{/if}
|
||||
</svelte:fragment>
|
||||
</Header>
|
||||
|
||||
<style lang="scss">
|
||||
.chat-header {
|
||||
display: flex;
|
||||
width: 100%;
|
||||
height: 4rem;
|
||||
min-height: 4rem;
|
||||
max-height: 4rem;
|
||||
border-bottom: 1px solid var(--next-panel-color-border);
|
||||
}
|
||||
</style>
|
||||
@@ -1,54 +0,0 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { Card } from '@hcengineering/card'
|
||||
import { NotificationContext } from '@hcengineering/communication-types'
|
||||
import { createNotificationContextsQuery } from '@hcengineering/presentation'
|
||||
import { Presence } from '@hcengineering/presence-resources'
|
||||
|
||||
import ChatHeader from './ChatHeader.svelte'
|
||||
import ChatBody from './ChatBody.svelte'
|
||||
import ChatFooter from './ChatFooter.svelte'
|
||||
|
||||
export let card: Card
|
||||
|
||||
const contextsQuery = createNotificationContextsQuery()
|
||||
|
||||
let footerHeight: number | undefined = undefined
|
||||
let context: NotificationContext | undefined = undefined
|
||||
let isLoaded = false
|
||||
let cardId = card._id
|
||||
|
||||
$: if (cardId !== card._id) {
|
||||
cardId = card._id
|
||||
context = undefined
|
||||
isLoaded = false
|
||||
}
|
||||
|
||||
$: contextsQuery.query({ card: cardId, limit: 1 }, (res) => {
|
||||
context = res.getResult()[0]
|
||||
isLoaded = true
|
||||
})
|
||||
</script>
|
||||
|
||||
<Presence object={card} />
|
||||
<ChatHeader {card} />
|
||||
{#if isLoaded}
|
||||
{#key card._id}
|
||||
<ChatBody {card} {footerHeight} {context} />
|
||||
{/key}
|
||||
{/if}
|
||||
<ChatFooter {card} bind:height={footerHeight} />
|
||||
@@ -1,186 +0,0 @@
|
||||
<!--
|
||||
// Copyright © 2025 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 { closeWidget, WidgetState } from '@hcengineering/workbench-resources'
|
||||
import { Widget } from '@hcengineering/workbench'
|
||||
import { getClient, createQuery, getCommunicationClient, createMessagesQuery } from '@hcengineering/presentation'
|
||||
import cardPlugin, { type Card } from '@hcengineering/card'
|
||||
import { Message, CardID } from '@hcengineering/communication-types'
|
||||
import { MessagePresenter, MessageInput, Divider, UploadedFile } from '@hcengineering/ui-next'
|
||||
import { fillDefaults, MarkupBlobRef, Ref, SortingOrder } from '@hcengineering/core'
|
||||
import { makeRank } from '@hcengineering/rank'
|
||||
import { employeeByPersonIdStore } from '@hcengineering/contact-resources'
|
||||
import { getEmployeeBySocialId } from '@hcengineering/contact'
|
||||
|
||||
import { ChatWidgetData } from '../types'
|
||||
import chat from '../plugin'
|
||||
import ChatHeader from './ChatHeader.svelte'
|
||||
import ChatBody from './ChatBody.svelte'
|
||||
import { createThreadTitle } from '../utils'
|
||||
import ChatFooter from './ChatFooter.svelte'
|
||||
|
||||
export let widget: Widget | undefined
|
||||
export let widgetState: WidgetState | undefined
|
||||
export let height: string
|
||||
export let width: string
|
||||
|
||||
const client = getClient()
|
||||
const hierarchy = client.getHierarchy()
|
||||
const communicationClient = getCommunicationClient()
|
||||
|
||||
const messageQuery = createMessagesQuery()
|
||||
const threadCardQuery = createQuery()
|
||||
const parentCardQuery = createQuery()
|
||||
|
||||
let data: ChatWidgetData | undefined = undefined
|
||||
|
||||
let threadCard: Card | undefined = undefined
|
||||
let parentCard: Card | undefined = undefined
|
||||
let message: Message | undefined = undefined
|
||||
|
||||
$: data = widgetState?.data as ChatWidgetData
|
||||
|
||||
$: if (data !== undefined) {
|
||||
messageQuery.query(
|
||||
{
|
||||
card: data.card,
|
||||
created: data.created,
|
||||
id: data.message,
|
||||
limit: 1,
|
||||
replies: true,
|
||||
files: true,
|
||||
reactions: true
|
||||
},
|
||||
(res) => {
|
||||
message = res.getResult()[0]
|
||||
}
|
||||
)
|
||||
|
||||
parentCardQuery.query(
|
||||
cardPlugin.class.Card,
|
||||
{ _id: data.card as Ref<Card> },
|
||||
(res) => {
|
||||
parentCard = res[0]
|
||||
},
|
||||
{ limit: 1 }
|
||||
)
|
||||
} else {
|
||||
message = undefined
|
||||
parentCard = undefined
|
||||
messageQuery.unsubscribe()
|
||||
parentCardQuery.unsubscribe()
|
||||
}
|
||||
|
||||
$: if (message?.thread != null) {
|
||||
threadCardQuery.query(
|
||||
cardPlugin.class.Card,
|
||||
{ _id: message.thread.thread as Ref<Card> },
|
||||
(res) => {
|
||||
threadCard = res[0]
|
||||
},
|
||||
{ limit: 1 }
|
||||
)
|
||||
} else {
|
||||
threadCard = undefined
|
||||
threadCardQuery.unsubscribe()
|
||||
}
|
||||
|
||||
$: if (widget === undefined || data === undefined) {
|
||||
closeWidget(chat.ids.ChatWidget)
|
||||
}
|
||||
|
||||
async function handleSubmit (markdown: string, files: UploadedFile[]): Promise<void> {
|
||||
if (message === undefined || data === undefined) return
|
||||
const { card } = data
|
||||
if (card === undefined || parentCard === undefined) return
|
||||
|
||||
let threadId: CardID | undefined = message.thread?.thread
|
||||
if (threadId == null) {
|
||||
const author =
|
||||
$employeeByPersonIdStore.get(message.creator) ?? (await getEmployeeBySocialId(client, message.creator))
|
||||
const lastOne = await client.findOne(cardPlugin.class.Card, {}, { sort: { rank: SortingOrder.Descending } })
|
||||
const title = createThreadTitle(message, parentCard)
|
||||
const data = fillDefaults(
|
||||
hierarchy,
|
||||
{
|
||||
title,
|
||||
rank: makeRank(lastOne?.rank, undefined),
|
||||
content: '' as MarkupBlobRef,
|
||||
parent: parentCard._id
|
||||
},
|
||||
chat.masterTag.Thread
|
||||
)
|
||||
threadId = (await client.createDoc(chat.masterTag.Thread, cardPlugin.space.Default, data)) as CardID
|
||||
|
||||
await communicationClient.createThread(card, message.id, message.created, threadId)
|
||||
if (author?.active === true && author?.personUuid !== undefined) {
|
||||
await communicationClient.addCollaborators(threadId, chat.masterTag.Thread, [author.personUuid])
|
||||
}
|
||||
}
|
||||
|
||||
if (threadId != null) {
|
||||
const { id, created } = await communicationClient.createMessage(threadId, chat.masterTag.Thread, markdown)
|
||||
for (const file of files) {
|
||||
await communicationClient.createFile(threadId, id, created, file.blobId, file.type, file.filename, file.size)
|
||||
}
|
||||
}
|
||||
}
|
||||
let footerHeight: number | undefined = undefined
|
||||
</script>
|
||||
|
||||
{#if widget && data && data.message}
|
||||
<div class="chat-widget" style:width style:height>
|
||||
<ChatHeader card={threadCard} icon={chat.icon.Thread} title={data.name} canClose on:close />
|
||||
{#if message && parentCard}
|
||||
<div class="mt-4" />
|
||||
<MessagePresenter {message} card={parentCard} replies={false} />
|
||||
<Divider />
|
||||
|
||||
<div class="messages">
|
||||
<ChatBody
|
||||
card={threadCard}
|
||||
bottomStart={false}
|
||||
showDates={false}
|
||||
overlyColor="var(--next-background-color)"
|
||||
{footerHeight}
|
||||
/>
|
||||
</div>
|
||||
<ChatFooter card={threadCard} bind:height={footerHeight} onSubmit={handleSubmit} />
|
||||
{/if}
|
||||
</div>
|
||||
{/if}
|
||||
|
||||
<style lang="scss">
|
||||
.chat-widget {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
min-height: 0;
|
||||
background: var(--next-background-color);
|
||||
}
|
||||
|
||||
.messages {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.footer {
|
||||
border-top: 1px solid var(--next-divider-color);
|
||||
padding: 1.25rem 1rem 0 1rem;
|
||||
}
|
||||
</style>
|
||||
@@ -1,58 +0,0 @@
|
||||
<!--
|
||||
// Copyright © 2024 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 { Loading, Scroller } from '@hcengineering/ui'
|
||||
|
||||
export let scroller: Scroller | undefined | null = undefined
|
||||
export let scrollDiv: HTMLDivElement | undefined | null = undefined
|
||||
export let contentDiv: HTMLDivElement | undefined | null = undefined
|
||||
export let bottomStart: boolean = true
|
||||
export let isLoading: boolean = false
|
||||
export let overlyColor: string = 'var(--next-panel-color-background)'
|
||||
export let onScroll: () => void = () => {}
|
||||
export let onResize: () => void = () => {}
|
||||
</script>
|
||||
|
||||
{#if isLoading}
|
||||
<div class="overlay" style:background-color={overlyColor}>
|
||||
<Loading />
|
||||
</div>
|
||||
{/if}
|
||||
<Scroller
|
||||
bind:this={scroller}
|
||||
bind:divScroll={scrollDiv}
|
||||
bind:divBox={contentDiv}
|
||||
scrollDirection="vertical-reverse"
|
||||
noStretch={true}
|
||||
{bottomStart}
|
||||
disableOverscroll
|
||||
disablePointerEventsOnScroll
|
||||
{onScroll}
|
||||
{onResize}
|
||||
>
|
||||
<slot />
|
||||
</Scroller>
|
||||
|
||||
<style lang="scss">
|
||||
.overlay {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
position: absolute;
|
||||
z-index: 9999;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
</style>
|
||||
@@ -16,11 +16,14 @@
|
||||
import { type Resources } from '@hcengineering/platform'
|
||||
|
||||
import ChatApplication from './components/ChatApplication.svelte'
|
||||
import ChatWidget from './components/ChatWidget.svelte'
|
||||
import { resolveLocation, resolveLocationData } from './location'
|
||||
|
||||
export default async (): Promise<Resources> => ({
|
||||
component: {
|
||||
ChatApplication,
|
||||
ChatWidget
|
||||
ChatApplication
|
||||
},
|
||||
resolver: {
|
||||
Location: resolveLocation,
|
||||
LocationData: resolveLocationData
|
||||
}
|
||||
})
|
||||
|
||||
@@ -13,54 +13,42 @@
|
||||
// limitations under the License.
|
||||
//
|
||||
|
||||
import { type Card, type MasterTag } from '@hcengineering/card'
|
||||
import type { Doc, Ref } from '@hcengineering/core'
|
||||
import { navigate, type Location, getCurrentResolvedLocation } from '@hcengineering/ui'
|
||||
import cardPlugin, { type Card, type MasterTag } from '@hcengineering/card'
|
||||
import type { Class, Doc, Ref } from '@hcengineering/core'
|
||||
import { navigate, getCurrentResolvedLocation, type Location, type ResolvedLocation } from '@hcengineering/ui'
|
||||
import { chatId } from '@hcengineering/chat'
|
||||
import { getClient } from '@hcengineering/presentation'
|
||||
import { type Message } from '@hcengineering/communication-types'
|
||||
import workbench from '@hcengineering/workbench'
|
||||
import { openWidget } from '@hcengineering/workbench-resources'
|
||||
|
||||
import chat from './plugin'
|
||||
import { type ChatWidgetData } from './types'
|
||||
import { createThreadTitle } from './utils'
|
||||
|
||||
export function decodeURI (value: string): ['type', Ref<MasterTag>] | ['card', Ref<Card>] {
|
||||
return decodeURIComponent(value).split('|') as any
|
||||
}
|
||||
|
||||
export function encodeURI (type: 'type' | 'card', ref: Ref<Doc>): string {
|
||||
return [type, ref].join('|')
|
||||
}
|
||||
import { type LocationData } from '@hcengineering/workbench'
|
||||
import { encodeObjectURI, decodeObjectURI } from '@hcengineering/view'
|
||||
import { accessDeniedStore } from '@hcengineering/view-resources'
|
||||
|
||||
export function getCardIdFromLocation (loc: Location): Ref<Card> | undefined {
|
||||
if (loc.path[2] !== chatId) {
|
||||
return undefined
|
||||
}
|
||||
const [type, ref] = decodeURI(loc.path[3])
|
||||
if (type !== 'card') {
|
||||
const [_id, _class] = decodeObjectURI(loc.path[3])
|
||||
if (_class !== cardPlugin.class.Card) {
|
||||
return undefined
|
||||
}
|
||||
return ref
|
||||
return _id as Ref<Card>
|
||||
}
|
||||
|
||||
export function getTypeIdFromLocation (loc: Location): Ref<MasterTag> | undefined {
|
||||
if (loc.path[2] !== chatId) {
|
||||
return undefined
|
||||
}
|
||||
const [type, ref] = decodeURI(loc.path[3])
|
||||
if (type !== 'type') {
|
||||
const [_id, _class] = decodeObjectURI(loc.path[3])
|
||||
if (_class !== cardPlugin.class.MasterTag) {
|
||||
return undefined
|
||||
}
|
||||
return ref
|
||||
return _id as Ref<MasterTag>
|
||||
}
|
||||
|
||||
export function navigateToCard (_id: Ref<Card>): void {
|
||||
const loc = getCurrentResolvedLocation()
|
||||
|
||||
loc.path[2] = chatId
|
||||
loc.path[3] = encodeURI('card', _id)
|
||||
loc.path[3] = encodeObjectURI(_id, cardPlugin.class.Card)
|
||||
delete loc.query?.message
|
||||
|
||||
navigate(loc)
|
||||
@@ -70,25 +58,74 @@ export function navigateToType (_id: Ref<MasterTag>): void {
|
||||
const loc = getCurrentResolvedLocation()
|
||||
|
||||
loc.path[2] = chatId
|
||||
loc.path[3] = encodeURI('type', _id)
|
||||
loc.path[3] = encodeObjectURI(_id, cardPlugin.class.MasterTag)
|
||||
delete loc.query?.message
|
||||
|
||||
navigate(loc)
|
||||
}
|
||||
|
||||
export async function openThreadInSidebar (message: Message, parent: Card): Promise<void> {
|
||||
const client = getClient()
|
||||
|
||||
const widget = client.getModel().findAllSync(workbench.class.Widget, { _id: chat.ids.ChatWidget })[0]
|
||||
if (widget === undefined) return
|
||||
|
||||
const data: ChatWidgetData = {
|
||||
id: `${message.card}-${message.id}`,
|
||||
name: createThreadTitle(message, parent),
|
||||
message: message.id,
|
||||
created: message.created,
|
||||
card: message.card
|
||||
export async function resolveLocation (loc: Location): Promise<ResolvedLocation | undefined> {
|
||||
if (loc.path[2] !== chatId) {
|
||||
return undefined
|
||||
}
|
||||
|
||||
openWidget(widget, data)
|
||||
const [_id, _class] = decodeObjectURI(loc.path[3])
|
||||
|
||||
if (_id != null && _class != null && _id !== '' && _class !== '') {
|
||||
return await generateLocation(loc, _id, _class)
|
||||
}
|
||||
}
|
||||
|
||||
async function generateLocation (
|
||||
loc: Location,
|
||||
_id: Ref<Doc>,
|
||||
_class: Ref<Class<Doc>>
|
||||
): Promise<ResolvedLocation | undefined> {
|
||||
const client = getClient()
|
||||
const doc = await client.findOne(_class, { _id })
|
||||
if (doc === undefined) {
|
||||
accessDeniedStore.set(true)
|
||||
return undefined
|
||||
}
|
||||
const appComponent = loc.path[0] ?? ''
|
||||
const workspace = loc.path[1] ?? ''
|
||||
|
||||
return {
|
||||
loc: {
|
||||
path: [appComponent, workspace, chatId, encodeObjectURI(_id, _class)],
|
||||
fragment: undefined
|
||||
},
|
||||
defaultLocation: {
|
||||
path: [appComponent, workspace, chatId, encodeObjectURI(_id, _class)],
|
||||
fragment: undefined
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export async function resolveLocationData (loc: Location): Promise<LocationData> {
|
||||
const cardId = getCardIdFromLocation(loc)
|
||||
const typeId = getTypeIdFromLocation(loc)
|
||||
const client = getClient()
|
||||
|
||||
if (cardId !== undefined) {
|
||||
const object = await client.findOne(cardPlugin.class.Card, { _id: cardId })
|
||||
|
||||
if (object === undefined) {
|
||||
return {}
|
||||
}
|
||||
|
||||
return { name: object.title }
|
||||
}
|
||||
|
||||
if (typeId !== undefined) {
|
||||
const object = await client.findOne(cardPlugin.class.MasterTag, { _id: typeId })
|
||||
|
||||
if (object === undefined) {
|
||||
return {}
|
||||
}
|
||||
|
||||
return { nameIntl: object.label }
|
||||
}
|
||||
|
||||
return {}
|
||||
}
|
||||
|
||||
@@ -40,8 +40,8 @@
|
||||
"dependencies": {
|
||||
"@hcengineering/analytics": "^0.6.0",
|
||||
"@hcengineering/client": "^0.6.18",
|
||||
"@hcengineering/communication-sdk-types": "0.1.172",
|
||||
"@hcengineering/communication-types": "0.1.172",
|
||||
"@hcengineering/communication-sdk-types": "0.1.174",
|
||||
"@hcengineering/communication-types": "0.1.174",
|
||||
"@hcengineering/core": "^0.6.32",
|
||||
"@hcengineering/platform": "^0.6.11",
|
||||
"@hcengineering/rpc": "^0.6.5",
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
module.exports = {
|
||||
extends: ['./node_modules/@hcengineering/platform-rig/profiles/assets/eslint.config.json'],
|
||||
parserOptions: {
|
||||
tsconfigRootDir: __dirname,
|
||||
project: './tsconfig.json'
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
{
|
||||
"$schema": "https://developer.microsoft.com/json-schemas/rig-package/rig.schema.json",
|
||||
"rigPackageName": "@hcengineering/platform-rig",
|
||||
"rigProfile": "assets"
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
module.exports = {
|
||||
preset: 'ts-jest',
|
||||
testEnvironment: 'node',
|
||||
testMatch: ['**/?(*.)+(spec|test).[jt]s?(x)'],
|
||||
roots: ["./src"],
|
||||
coverageReporters: ["text-summary", "html"]
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Zprávy",
|
||||
"FirstMessages": "První zprávy",
|
||||
"LatestMessages": "Poslední zprávy"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Nachrichten",
|
||||
"FirstMessages": "Erste Nachrichten",
|
||||
"LatestMessages": "Neueste Nachrichten"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Messages",
|
||||
"FirstMessages": "First messages",
|
||||
"LatestMessages": "Latest messages"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Mensajes",
|
||||
"FirstMessages": "Primeros Mensajes",
|
||||
"LatestMessages": "Últimos Mensajes"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Messages",
|
||||
"FirstMessages": "Premiers messages",
|
||||
"LatestMessages": "Derniers messages"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Messaggi",
|
||||
"FirstMessages": "Primi Messaggi",
|
||||
"LatestMessages": "Ultimi Messaggi"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "メッセージ",
|
||||
"FirstMessages": "最初のメッセージ",
|
||||
"LatestMessages": "最新のメッセージ"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Mensagens",
|
||||
"FirstMessages": "Primeiras Mensagens",
|
||||
"LatestMessages": "Últimas Mensagens"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "Сообщения",
|
||||
"FirstMessages": "Первые сообщения",
|
||||
"LatestMessages": "Последние сообщения"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"string": {
|
||||
"Messages": "消息",
|
||||
"FirstMessages": "第一条消息",
|
||||
"LatestMessages": "最新消息"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
{
|
||||
"name": "@hcengineering/communication-assets",
|
||||
"version": "0.6.0",
|
||||
"main": "src/index.ts",
|
||||
"author": "Copyright © Hardcore Engineering Inc.",
|
||||
"template": "@hcengineering/assets-package",
|
||||
"license": "EPL-2.0",
|
||||
"scripts": {
|
||||
"build": "compile",
|
||||
"test": "jest --passWithNoTests --silent",
|
||||
"build:docs": "",
|
||||
"format": "format src",
|
||||
"build:watch": "compile",
|
||||
"_phase:build": "compile transpile src",
|
||||
"_phase:test": "jest --passWithNoTests --silent",
|
||||
"_phase:format": "format src",
|
||||
"_phase:validate": "compile validate"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@hcengineering/platform-rig": "^0.6.0",
|
||||
"@typescript-eslint/eslint-plugin": "^6.11.0",
|
||||
"@typescript-eslint/parser": "^6.11.0",
|
||||
"eslint-config-standard-with-typescript": "^40.0.0",
|
||||
"eslint-plugin-import": "^2.26.0",
|
||||
"eslint-plugin-n": "^15.4.0",
|
||||
"eslint-plugin-promise": "^6.1.1",
|
||||
"eslint": "^8.54.0",
|
||||
"prettier": "^3.1.0",
|
||||
"@types/node": "~20.11.16",
|
||||
"jest": "^29.7.0",
|
||||
"ts-jest": "^29.1.1",
|
||||
"@types/jest": "^29.5.5",
|
||||
"typescript": "^5.3.3"
|
||||
},
|
||||
"dependencies": {
|
||||
"@hcengineering/platform": "^0.6.11",
|
||||
"@hcengineering/communication": "^0.6.0"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
import { makeLocalesTest } from '@hcengineering/platform'
|
||||
|
||||
it(
|
||||
'Locales are equale',
|
||||
makeLocalesTest((lang) => import(`../../lang/${lang}.json`))
|
||||
)
|
||||
@@ -0,0 +1,19 @@
|
||||
//
|
||||
// Copyright © 2025 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 { addStringsLoader } from '@hcengineering/platform'
|
||||
import { communicationId } from '@hcengineering/communication'
|
||||
|
||||
addStringsLoader(communicationId, async (lang: string) => await import(`../lang/${lang}.json`))
|
||||
@@ -0,0 +1,11 @@
|
||||
{
|
||||
"extends": "./node_modules/@hcengineering/platform-rig/profiles/assets/tsconfig.json",
|
||||
|
||||
"compilerOptions": {
|
||||
"rootDir": "./src",
|
||||
"outDir": "./lib",
|
||||
"declarationDir": "./types",
|
||||
"types": ["node", "jest"],
|
||||
"tsBuildInfoFile": ".build/build.tsbuildinfo"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,4 @@
|
||||
module.exports = {
|
||||
extends: ['./node_modules/@hcengineering/platform-rig/profiles/ui/eslint.config.json'],
|
||||
parserOptions: { tsconfigRootDir: __dirname }
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
{
|
||||
"$schema": "http://json-schema.org/draft-04/schema#",
|
||||
"trailingComma": "none",
|
||||
"tabWidth": 2,
|
||||
"semi": false,
|
||||
"singleQuote": true,
|
||||
"printWidth": 120,
|
||||
"useTabs": false,
|
||||
"bracketSpacing": true,
|
||||
"proseWrap": "preserve",
|
||||
"plugins": [
|
||||
"prettier-plugin-svelte"
|
||||
],
|
||||
"overrides": [
|
||||
{
|
||||
"files": "*.svelte",
|
||||
"options": {
|
||||
"parser": "svelte"
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
{
|
||||
"$schema": "https://developer.microsoft.com/json-schemas/rig-package/rig.schema.json",
|
||||
"rigPackageName": "@hcengineering/platform-rig",
|
||||
"rigProfile": "ui"
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
module.exports = {
|
||||
preset: 'ts-jest',
|
||||
testEnvironment: 'node',
|
||||
testMatch: ['**/?(*.)+(spec|test).[jt]s?(x)']
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user