From 5f5dc63d2134d237b11ed96051dbfcd75430a281 Mon Sep 17 00:00:00 2001 From: Andrey Sobolev Date: Fri, 21 Jan 2022 16:05:55 +0700 Subject: [PATCH] Configurable Back reference (#848) Signed-off-by: Andrey Sobolev --- common/config/rush/pnpm-lock.yaml | 39 +++- models/all/package.json | 1 + models/all/src/index.ts | 2 + models/chunter/src/index.ts | 2 +- models/contact/package.json | 1 + models/contact/src/index.ts | 19 ++ models/contact/src/plugin.ts | 16 +- models/presentation/.eslintrc.js | 7 + models/presentation/.npmignore | 4 + models/presentation/config/rig.json | 18 ++ models/presentation/package.json | 35 ++++ models/presentation/src/index.ts | 40 +++++ models/presentation/src/plugin.ts | 23 +++ models/presentation/tsconfig.json | 8 + models/recruit/package.json | 3 +- models/recruit/src/index.ts | 7 + models/recruit/src/plugin.ts | 8 +- models/task/package.json | 3 +- models/task/src/index.ts | 46 ++--- models/task/src/plugin.ts | 8 +- packages/presentation/src/index.ts | 3 +- packages/presentation/src/plugin.ts | 13 +- packages/presentation/src/types.ts | 31 ++++ packages/text-editor/lang/en.json | 5 + packages/text-editor/package.json | 1 + .../src/components/MentionList.svelte | 108 ++++++++--- .../src/components/ReferenceInput.svelte | 71 +++++++- .../src/components/TextEditor.svelte | 168 +++++++----------- packages/text-editor/src/index.ts | 28 ++- packages/text-editor/src/plugin.ts | 28 +++ .../src/components/TxView.svelte | 3 +- plugins/contact-assets/lang/en.json | 5 +- plugins/contact-resources/src/index.ts | 44 +++-- plugins/contact-resources/src/plugin.ts | 3 +- plugins/recruit-assets/lang/en.json | 3 +- .../src/components/ApplicationItem.svelte | 49 +++++ plugins/recruit-resources/src/index.ts | 42 ++++- plugins/task-assets/lang/en.json | 3 +- .../src/components/TaskItem.svelte | 47 +++++ plugins/task-resources/src/index.ts | 70 ++++++-- plugins/task/src/index.ts | 2 - rush.json | 5 + server/core/src/storage.ts | 2 +- 43 files changed, 786 insertions(+), 238 deletions(-) create mode 100644 models/presentation/.eslintrc.js create mode 100644 models/presentation/.npmignore create mode 100644 models/presentation/config/rig.json create mode 100644 models/presentation/package.json create mode 100644 models/presentation/src/index.ts create mode 100644 models/presentation/src/plugin.ts create mode 100644 models/presentation/tsconfig.json create mode 100644 packages/presentation/src/types.ts create mode 100644 packages/text-editor/lang/en.json create mode 100644 packages/text-editor/src/plugin.ts create mode 100644 plugins/recruit-resources/src/components/ApplicationItem.svelte create mode 100644 plugins/task-resources/src/components/TaskItem.svelte diff --git a/common/config/rush/pnpm-lock.yaml b/common/config/rush/pnpm-lock.yaml index eade30a229..e9efd89f1a 100644 --- a/common/config/rush/pnpm-lock.yaml +++ b/common/config/rush/pnpm-lock.yaml @@ -55,6 +55,7 @@ specifiers: '@rush-temp/model-gmail': file:./projects/model-gmail.tgz '@rush-temp/model-inventory': file:./projects/model-inventory.tgz '@rush-temp/model-lead': file:./projects/model-lead.tgz + '@rush-temp/model-presentation': file:./projects/model-presentation.tgz '@rush-temp/model-recruit': file:./projects/model-recruit.tgz '@rush-temp/model-rig': file:./projects/model-rig.tgz '@rush-temp/model-server-attachment': file:./projects/model-server-attachment.tgz @@ -239,6 +240,7 @@ dependencies: '@rush-temp/model-gmail': file:projects/model-gmail.tgz_typescript@4.5.4 '@rush-temp/model-inventory': file:projects/model-inventory.tgz_typescript@4.5.4 '@rush-temp/model-lead': file:projects/model-lead.tgz_typescript@4.5.4 + '@rush-temp/model-presentation': file:projects/model-presentation.tgz_typescript@4.5.4 '@rush-temp/model-recruit': file:projects/model-recruit.tgz_typescript@4.5.4 '@rush-temp/model-rig': file:projects/model-rig.tgz_37f79b97d0d86442e45d380c86f520c5 '@rush-temp/model-server-attachment': file:projects/model-server-attachment.tgz_typescript@4.5.4 @@ -11634,7 +11636,7 @@ packages: dev: false file:projects/model-all.tgz_typescript@4.5.4: - resolution: {integrity: sha512-Z4F3zvl3i5iZUuhvKo1+SlVy9Urq09lVL4XsyY1zAwk14Af42uf5CVbbubPiSuLt4SevW1StJ5c08y4vztbfQA==, tarball: file:projects/model-all.tgz} + resolution: {integrity: sha512-xDbSAT10XpV9IMIWZmkZF1DKtDmPuh++4I5oxtxRHGrrdJ1h0J37nkAmZ6AayfWgqaCXG8EBn+SplvLw07HESg==, tarball: file:projects/model-all.tgz} id: file:projects/model-all.tgz name: '@rush-temp/model-all' version: 0.0.0 @@ -11701,7 +11703,7 @@ packages: dev: false file:projects/model-contact.tgz_typescript@4.5.4: - resolution: {integrity: sha512-GD5NmMEaz2KD79NdbNlQTbmuc98hxeV0cwV8xgRtCZnbeNrDw4h71yUik4vGNLsgha8ezy2oefrdi5aET1wbig==, tarball: file:projects/model-contact.tgz} + resolution: {integrity: sha512-a2k6USkc9xrm3ba78A0pOps3X4Ox8A+uHm3cdNpfrSA8ihdfU9p6imeFr+ZotWF8YCcnwagz9sVHpT5dtmH4Mg==, tarball: file:projects/model-contact.tgz} id: file:projects/model-contact.tgz name: '@rush-temp/model-contact' version: 0.0.0 @@ -11826,8 +11828,29 @@ packages: - typescript dev: false + file:projects/model-presentation.tgz_typescript@4.5.4: + resolution: {integrity: sha512-cBkfqfxIgaViuDI4bj0NDuVg1NnzoSjL2mxvRRRn1Dnqkq+2K00cKyx67Pil9dHwH636h2HEYKoM4VNsT3Os1w==, tarball: file:projects/model-presentation.tgz} + id: file:projects/model-presentation.tgz + name: '@rush-temp/model-presentation' + version: 0.0.0 + dependencies: + '@rushstack/heft': 0.41.8 + '@types/heft-jest': 1.0.2 + '@typescript-eslint/eslint-plugin': 5.7.0_c25e8c1f4f4f7aaed27aa6f9ce042237 + '@typescript-eslint/parser': 5.7.0_eslint@7.32.0+typescript@4.5.4 + eslint: 7.32.0 + eslint-config-standard-with-typescript: 21.0.1_ce2fa0c4dfa1c256100cababd749a13a + eslint-plugin-import: 2.25.3_eslint@7.32.0 + eslint-plugin-node: 11.1.0_eslint@7.32.0 + eslint-plugin-promise: 5.2.0_eslint@7.32.0 + prettier: 2.5.1 + transitivePeerDependencies: + - supports-color + - typescript + dev: false + file:projects/model-recruit.tgz_typescript@4.5.4: - resolution: {integrity: sha512-wIeXWWUD1Lwg8R43hEvmJzZ/ooN4DWdqv1+2vPFDZU/1xKwlW7Gqu1hZM5qUUVHbLLgMOmHsHDscPfn7tB11UQ==, tarball: file:projects/model-recruit.tgz} + resolution: {integrity: sha512-M2V190p42TMpwBagu8ts2iLvDu2hFprTiMX2i/KIwANipE9lJGHmjYlvh7HEGsdSYbeFavMuWdqoUNWjnCjy1Q==, tarball: file:projects/model-recruit.tgz} id: file:projects/model-recruit.tgz name: '@rush-temp/model-recruit' version: 0.0.0 @@ -11951,7 +11974,7 @@ packages: dev: false file:projects/model-task.tgz_typescript@4.5.4: - resolution: {integrity: sha512-+R3a/p9KvLJRF7CCbFwZer5TPDbBAjpTW85JDRrpV4sL2bEQIgtgtoYYwtd8dMyqCld1MToYesR9WYvwHmVGFw==, tarball: file:projects/model-task.tgz} + resolution: {integrity: sha512-yIegyos933cu1NpvP/oFomGd8Yo9wKWjyoQyxNO26ERynPFdYIZ7yRKeiIpVp/P2T2xT3M9510GfdWJx6/MkgA==, tarball: file:projects/model-task.tgz} id: file:projects/model-task.tgz name: '@rush-temp/model-task' version: 0.0.0 @@ -12229,7 +12252,7 @@ packages: dev: false file:projects/prod.tgz_sass@1.45.0+typescript@4.5.4: - resolution: {integrity: sha512-WxsSu4KtdtPTf1EJkHs/CJFDHiU0AgfGMmyOm66DFGc0cWOiJlgoCcw9TuCNaQPCBQ/ldbNYbfpj01N4iZFYuA==, tarball: file:projects/prod.tgz} + resolution: {integrity: sha512-FWLkhyyIA2ZiXuydQap4fYlvfq02Q18A0fjVgVmy/7Wedebed2Xj6n2uQVjDVN50a5EP+5CutRcLAuxs7bI4Vw==, tarball: file:projects/prod.tgz} id: file:projects/prod.tgz name: '@rush-temp/prod' version: 0.0.0 @@ -12495,7 +12518,7 @@ packages: dev: false file:projects/server.tgz: - resolution: {integrity: sha512-e8Oeh7z0NrGebPnTPZDsh4H6UUwDv2F4ywRw2o6GW7r3iXd1iK4nbxqs1bG7DvHy7kpY+jWk6tMpFSYJ+RXOrg==, tarball: file:projects/server.tgz} + resolution: {integrity: sha512-5U67EYHkOoUqolvKMKSN1++52yfIzKPOIG2pmnbra2Ffcg9O/7UCat9eBIUx8U+n1998DnVm+c9H3yHadlOdsw==, tarball: file:projects/server.tgz} name: '@rush-temp/server' version: 0.0.0 dependencies: @@ -12723,7 +12746,7 @@ packages: dev: false file:projects/text-editor.tgz_096c09b0b673a57c275d9767a12070b1: - resolution: {integrity: sha512-Fg9TwM9Q/v+2QLbOwTuBAhjI0/4Lm34ksUW2R0PjuY0WTUGk/ZbKALm2HJAr+fQgjd8B1FXjcFXlidoOIWQ9jA==, tarball: file:projects/text-editor.tgz} + resolution: {integrity: sha512-mHTzsgBUTd2d3Y8xW1y8GOTLU0r4IyOsF7RpV1N4GVwaqnCZSxuFdC/T7PqX33XYI0hD6q+0KNegRs+MzvOeeg==, tarball: file:projects/text-editor.tgz} id: file:projects/text-editor.tgz name: '@rush-temp/text-editor' version: 0.0.0 @@ -12805,7 +12828,7 @@ packages: dev: false file:projects/tool.tgz: - resolution: {integrity: sha512-Zwy6rf7v5DtpINp3IaWvHYoEVdkaQMi2n837scjAUyUjp21wMQshZudzu/K00Nfi4vI/Z40Ue8hG6LrcrUHQzA==, tarball: file:projects/tool.tgz} + resolution: {integrity: sha512-dfzDNJuguQfZyQh/Z9IkPneooJEK0O5kQcEnqOyPiJIvv/HPK2dNw2U97BrWhjylNqTMxDziWY2zkMXiUdEkTg==, tarball: file:projects/tool.tgz} name: '@rush-temp/tool' version: 0.0.0 dependencies: diff --git a/models/all/package.json b/models/all/package.json index 3295e47a43..38d1b99845 100644 --- a/models/all/package.json +++ b/models/all/package.json @@ -47,6 +47,7 @@ "@anticrm/model-attachment": "~0.6.0", "@anticrm/model-gmail": "~0.6.0", "@anticrm/model-inventory": "~0.6.0", + "@anticrm/model-presentation": "~0.6.0", "@anticrm/core": "~0.6.13" } } diff --git a/models/all/src/index.ts b/models/all/src/index.ts index 4561c14698..883fd19afe 100644 --- a/models/all/src/index.ts +++ b/models/all/src/index.ts @@ -28,6 +28,7 @@ import { createModel as attachmentModel } from '@anticrm/model-attachment' import { createModel as leadModel } from '@anticrm/model-lead' import { createModel as gmailModel } from '@anticrm/model-gmail' import { createModel as inventoryModel } from '@anticrm/model-inventory' +import { createModel as presentationModel } from '@anticrm/model-presentation' import { createModel as serverCoreModel } from '@anticrm/model-server-core' import { createModel as serverAttachmentModel } from '@anticrm/model-server-attachment' @@ -52,6 +53,7 @@ telegramModel(builder) leadModel(builder) gmailModel(builder) inventoryModel(builder) +presentationModel(builder) serverCoreModel(builder) serverAttachmentModel(builder) diff --git a/models/chunter/src/index.ts b/models/chunter/src/index.ts index 2408628b33..6549e30e09 100644 --- a/models/chunter/src/index.ts +++ b/models/chunter/src/index.ts @@ -143,7 +143,7 @@ export function createModel (builder: Builder): void { component: chunter.activity.TxBacklinkCreate, label: chunter.string.MentionedIn, labelComponent: chunter.activity.TxBacklinkReference, - display: 'content', + display: 'emphasized', editable: false, hideOnRemove: true }, chunter.ids.TxCommentCreate) diff --git a/models/contact/package.json b/models/contact/package.json index 8fb9014113..1a5352d498 100644 --- a/models/contact/package.json +++ b/models/contact/package.json @@ -30,6 +30,7 @@ "@anticrm/model-workbench": "~0.6.0", "@anticrm/model-attachment": "~0.6.0", "@anticrm/model-view": "~0.6.0", + "@anticrm/model-presentation": "~0.6.0", "@anticrm/model": "~0.6.0", "@anticrm/core": "~0.6.11", "@anticrm/ui": "~0.6.0", diff --git a/models/contact/src/index.ts b/models/contact/src/index.ts index c7a04c5dab..020cd96f60 100644 --- a/models/contact/src/index.ts +++ b/models/contact/src/index.ts @@ -34,6 +34,7 @@ import workbench from '@anticrm/model-workbench' import view from '@anticrm/model-view' import attachment from '@anticrm/model-attachment' import { ids as contact } from './plugin' +import presentation from '@anticrm/model-presentation' export const DOMAIN_CONTACT = 'contact' as Domain @@ -234,6 +235,24 @@ export function createModel (builder: Builder): void { builder.mixin(contact.class.Contact, core.class.Class, view.mixin.AttributePresenter, { presenter: contact.component.ContactPresenter }) + + builder.createDoc(presentation.class.ObjectSearchCategory, core.space.Model, { + icon: contact.icon.Person, + label: contact.string.SearchEmployee, + query: contact.completion.EmployeeQuery + }, contact.completion.EmployeeCategory) + + builder.createDoc(presentation.class.ObjectSearchCategory, core.space.Model, { + icon: contact.icon.Person, + label: contact.string.SearchPerson, + query: contact.completion.PersonQuery + }, contact.completion.PersonCategory) + + builder.createDoc(presentation.class.ObjectSearchCategory, core.space.Model, { + icon: contact.icon.Company, + label: contact.string.SearchOrganization, + query: contact.completion.OrganizationQuery + }, contact.completion.OrganizationCategory) } export { contact as default } diff --git a/models/contact/src/plugin.ts b/models/contact/src/plugin.ts index a6ded5844b..ea94f61a2b 100644 --- a/models/contact/src/plugin.ts +++ b/models/contact/src/plugin.ts @@ -13,13 +13,14 @@ // limitations under the License. // -import { IntlString, mergeIds } from '@anticrm/platform' +import { IntlString, mergeIds, Resource } from '@anticrm/platform' import type { Ref, Class, Type } from '@anticrm/core' import contact, { contactId } from '@anticrm/contact' import type { Channel } from '@anticrm/contact' import type { AnyComponent } from '@anticrm/ui' import {} from '@anticrm/core' import { Application } from '@anticrm/workbench' +import { ObjectSearchCategory, ObjectSearchFactory } from '@anticrm/model-presentation' export const ids = mergeIds(contactId, contact, { app: { @@ -45,9 +46,20 @@ export const ids = mergeIds(contactId, contact, { Persons: '' as IntlString, Contacts: '' as IntlString, CreatePersons: '' as IntlString, - CreateOrganizations: '' as IntlString + CreateOrganizations: '' as IntlString, + SearchEmployee: '' as IntlString, + SearchPerson: '' as IntlString, + SearchOrganization: '' as IntlString }, class: { TypeChannel: '' as Ref>> + }, + completion: { + PersonQuery: '' as Resource, + EmployeeQuery: '' as Resource, + OrganizationQuery: '' as Resource, + EmployeeCategory: '' as Ref, + PersonCategory: '' as Ref, + OrganizationCategory: '' as Ref } }) diff --git a/models/presentation/.eslintrc.js b/models/presentation/.eslintrc.js new file mode 100644 index 0000000000..c3c2c49417 --- /dev/null +++ b/models/presentation/.eslintrc.js @@ -0,0 +1,7 @@ +module.exports = { + extends: ['./node_modules/@anticrm/model-rig/profiles/default/config/eslint.config.json'], + parserOptions: { + tsconfigRootDir: __dirname, + project: './tsconfig.json' + } +} diff --git a/models/presentation/.npmignore b/models/presentation/.npmignore new file mode 100644 index 0000000000..e3ec093c38 --- /dev/null +++ b/models/presentation/.npmignore @@ -0,0 +1,4 @@ +* +!/lib/** +!CHANGELOG.md +/lib/**/__tests__/ diff --git a/models/presentation/config/rig.json b/models/presentation/config/rig.json new file mode 100644 index 0000000000..e9a9ee9add --- /dev/null +++ b/models/presentation/config/rig.json @@ -0,0 +1,18 @@ +// The "rig.json" file directs tools to look for their config files in an external package. +// Documentation for this system: https://www.npmjs.com/package/@rushstack/rig-package +{ + "$schema": "https://developer.microsoft.com/json-schemas/rig-package/rig.schema.json", + + /** + * (Required) The name of the rig package to inherit from. + * It should be an NPM package name with the "-rig" suffix. + */ + "rigPackageName": "@anticrm/model-rig" + + /** + * (Optional) Selects a config profile from the rig package. The name must consist of + * lowercase alphanumeric words separated by hyphens, for example "sample-profile". + * If omitted, then the "default" profile will be used." + */ + // "rigProfile": "your-profile-name" +} diff --git a/models/presentation/package.json b/models/presentation/package.json new file mode 100644 index 0000000000..320000ceb7 --- /dev/null +++ b/models/presentation/package.json @@ -0,0 +1,35 @@ +{ + "name": "@anticrm/model-presentation", + "version": "0.6.0", + "main": "lib/index.js", + "author": "Anticrm Platform Contributors", + "license": "EPL-2.0", + "scripts": { + "build": "heft build", + "build:watch": "tsc", + "lint:fix": "eslint --fix src", + "lint": "eslint src", + "format": "prettier --write src && eslint --fix src" + }, + "devDependencies": { + "@anticrm/model-rig": "~0.6.0", + "@typescript-eslint/eslint-plugin": "^5.4.0", + "eslint-plugin-import": "^2.25.3", + "eslint-plugin-promise": "^5.1.1", + "eslint-plugin-node": "^11.1.0", + "eslint": "^7.32.0", + "@types/heft-jest": "^1.0.2", + "@typescript-eslint/parser": "^5.4.0", + "eslint-config-standard-with-typescript": "^21.0.1", + "prettier": "^2.4.1", + "@rushstack/heft": "^0.41.1" + }, + "dependencies": { + "@anticrm/core": "~0.6.11", + "@anticrm/model": "~0.6.0", + "@anticrm/platform": "~0.6.5", + "@anticrm/ui": "~0.6.0", + "@anticrm/presentation": "~0.6.0", + "@anticrm/model-core": "~0.6.0" + } +} diff --git a/models/presentation/src/index.ts b/models/presentation/src/index.ts new file mode 100644 index 0000000000..9372c73f2c --- /dev/null +++ b/models/presentation/src/index.ts @@ -0,0 +1,40 @@ +// +// Copyright © 2020 Anticrm Platform Contributors. +// +// Licensed under the Eclipse Public License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. You may +// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// +// See the License for the specific language governing permissions and +// limitations under the License. +// + +import { DOMAIN_MODEL } from '@anticrm/core' +import { Builder, Model } from '@anticrm/model' +import core, { TDoc } from '@anticrm/model-core' +import type { Asset, IntlString, Resource } from '@anticrm/platform' +// Import types to prevent .svelte components to being exposed to type typescript. +import { ObjectSearchCategory, ObjectSearchFactory } from '@anticrm/presentation/src/types' +import presentation from './plugin' + +export { default } from './plugin' +export { ObjectSearchCategory, ObjectSearchFactory } + +@Model(presentation.class.ObjectSearchCategory, core.class.Doc, DOMAIN_MODEL) +export class TObjectSearchCategory extends TDoc implements ObjectSearchCategory { + label!: IntlString + icon!: Asset + + // Query for documents with pattern + query!: Resource +} + +export function createModel (builder: Builder): void { + builder.createModel( + TObjectSearchCategory + ) +} diff --git a/models/presentation/src/plugin.ts b/models/presentation/src/plugin.ts new file mode 100644 index 0000000000..b46f993fe6 --- /dev/null +++ b/models/presentation/src/plugin.ts @@ -0,0 +1,23 @@ +// +// Copyright © 2020, 2021 Anticrm Platform Contributors. +// Copyright © 2021 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 { mergeIds } from '@anticrm/platform' +// Import plugin directly to prevent .svelte components to being exposed to type typescript. +import presentation, { presentationId } from '@anticrm/presentation/src/plugin' + +export default mergeIds(presentationId, presentation, { + +}) diff --git a/models/presentation/tsconfig.json b/models/presentation/tsconfig.json new file mode 100644 index 0000000000..1d60db76b4 --- /dev/null +++ b/models/presentation/tsconfig.json @@ -0,0 +1,8 @@ +{ + "extends": "./node_modules/@anticrm/model-rig/profiles/default/tsconfig.json", + + "compilerOptions": { + "rootDir": "./src", + "outDir": "./lib", + } +} \ No newline at end of file diff --git a/models/recruit/package.json b/models/recruit/package.json index 9611e808ba..dc4eb65fed 100644 --- a/models/recruit/package.json +++ b/models/recruit/package.json @@ -42,6 +42,7 @@ "@anticrm/view": "~0.6.0", "@anticrm/task": "~0.6.0", "@anticrm/model-task": "~0.6.0", - "@anticrm/workbench": "~0.6.1" + "@anticrm/workbench": "~0.6.1", + "@anticrm/model-presentation": "~0.6.0" } } diff --git a/models/recruit/src/index.ts b/models/recruit/src/index.ts index 631bacbdb5..372bd9c466 100644 --- a/models/recruit/src/index.ts +++ b/models/recruit/src/index.ts @@ -26,6 +26,7 @@ import workbench from '@anticrm/model-workbench' import type { IntlString } from '@anticrm/platform' import { Applicant, Candidate, Candidates, Vacancy } from '@anticrm/recruit' import recruit from './plugin' +import presentation from '@anticrm/model-presentation' @Model(recruit.class.Vacancy, task.class.SpaceWithStates) @UX(recruit.string.Vacancy, recruit.icon.Vacancy) @@ -281,6 +282,12 @@ export function createModel (builder: Builder): void { }, recruit.space.VacancyTemplates ) + + builder.createDoc(presentation.class.ObjectSearchCategory, core.space.Model, { + icon: recruit.icon.Application, + label: recruit.string.SearchApplication, + query: recruit.completion.ApplicationQuery + }, recruit.completion.ApplicationCategory) } export { default } from './plugin' diff --git a/models/recruit/src/plugin.ts b/models/recruit/src/plugin.ts index f8e771857c..e6e2725934 100644 --- a/models/recruit/src/plugin.ts +++ b/models/recruit/src/plugin.ts @@ -22,6 +22,7 @@ import { KanbanTemplate } from '@anticrm/task' import type { AnyComponent } from '@anticrm/ui' import type { Action } from '@anticrm/view' import { Application } from '@anticrm/workbench' +import { ObjectSearchFactory, ObjectSearchCategory } from '@anticrm/model-presentation' export default mergeIds(recruitId, recruit, { app: { @@ -36,7 +37,8 @@ export default mergeIds(recruitId, recruit, { string: { RecruitApplication: '' as IntlString, Vacancies: '' as IntlString, - CandidatePools: '' as IntlString + CandidatePools: '' as IntlString, + SearchApplication: '' as IntlString }, validator: { ApplicantValidator: '' as Resource<(doc: T, client: Client) => Promise> @@ -56,5 +58,9 @@ export default mergeIds(recruitId, recruit, { }, template: { DefaultVacancy: '' as Ref + }, + completion: { + ApplicationQuery: '' as Resource, + ApplicationCategory: '' as Ref } }) diff --git a/models/task/package.json b/models/task/package.json index 40953233da..4aa1a55b99 100644 --- a/models/task/package.json +++ b/models/task/package.json @@ -39,6 +39,7 @@ "@anticrm/task-resources": "~0.6.0", "@anticrm/model-chunter": "~0.6.0", "@anticrm/workbench": "~0.6.1", - "@anticrm/view": "~0.6.0" + "@anticrm/view": "~0.6.0", + "@anticrm/model-presentation": "~0.6.0" } } diff --git a/models/task/src/index.ts b/models/task/src/index.ts index 6fed442334..47da9eb949 100644 --- a/models/task/src/index.ts +++ b/models/task/src/index.ts @@ -14,53 +14,38 @@ // // To help typescript locate view plugin properly -import type { ActionTarget } from '@anticrm/view' - -import attachment from '@anticrm/model-attachment' import type { Employee } from '@anticrm/contact' import contact from '@anticrm/contact' import { Arr, Class, Doc, Domain, DOMAIN_MODEL, FindOptions, Ref, Space, Timestamp } from '@anticrm/core' import { Builder, - Collection, - Implements, + Collection, Hidden, Implements, Mixin, Model, - Prop, - Hidden, - TypeBoolean, + Prop, TypeBoolean, TypeDate, TypeRef, TypeString, UX } from '@anticrm/model' +import attachment from '@anticrm/model-attachment' import chunter from '@anticrm/model-chunter' import core, { TAttachedDoc, TClass, TDoc, TSpace } from '@anticrm/model-core' +import presentation from '@anticrm/model-presentation' import view from '@anticrm/model-view' import workbench from '@anticrm/model-workbench' import type { IntlString } from '@anticrm/platform' import type { - Kanban, - KanbanCard, - Project, - State, - Issue, - Sequence, - DoneState, - WonState, - LostState, - KanbanTemplateSpace, - StateTemplate, - DoneStateTemplate, - WonStateTemplate, - LostStateTemplate, - KanbanTemplate, - Task, - TodoItem + DoneState, DoneStateTemplate, Issue, Kanban, + KanbanCard, KanbanTemplate, KanbanTemplateSpace, LostState, LostStateTemplate, Project, Sequence, State, StateTemplate, Task, + TodoItem, WonState, WonStateTemplate } from '@anticrm/task' -import task from './plugin' import { AnyComponent } from '@anticrm/ui' +import type { ActionTarget } from '@anticrm/view' +import task from './plugin' +export { createDeps, createKanbanTemplate } from './creation' +export { taskOperation } from './migration' export { default } from './plugin' export const DOMAIN_TASK = 'task' as Domain @@ -519,7 +504,10 @@ export function createModel (builder: Builder): void { done: true } }) -} -export { taskOperation } from './migration' -export { createDeps, createKanbanTemplate } from './creation' + builder.createDoc(presentation.class.ObjectSearchCategory, core.space.Model, { + icon: task.icon.Task, + label: task.string.SearchTask, + query: task.completion.IssueQuery + }, task.completion.IssueCategory) +} diff --git a/models/task/src/plugin.ts b/models/task/src/plugin.ts index c12f606492..04de2c60b5 100644 --- a/models/task/src/plugin.ts +++ b/models/task/src/plugin.ts @@ -22,6 +22,7 @@ import task from '@anticrm/task-resources/src/plugin' import type { AnyComponent } from '@anticrm/ui' import { Application } from '@anticrm/workbench' import type { Action } from '@anticrm/view' +import { ObjectSearchCategory, ObjectSearchFactory } from '@anticrm/model-presentation' export default mergeIds(taskId, task, { app: { @@ -85,12 +86,17 @@ export default mergeIds(taskId, task, { MarkAsUndone: '' as IntlString, Kanban: '' as IntlString, ApplicationLabelTask: '' as IntlString, - Projects: '' as IntlString + Projects: '' as IntlString, + SearchTask: '' as IntlString }, space: { TasksPublic: '' as Ref }, template: { DefaultProject: '' as Ref + }, + completion: { + IssueQuery: '' as Resource, + IssueCategory: '' as Ref } }) diff --git a/packages/presentation/src/index.ts b/packages/presentation/src/index.ts index 20b0f02de0..62527f59ca 100644 --- a/packages/presentation/src/index.ts +++ b/packages/presentation/src/index.ts @@ -16,9 +16,10 @@ import { addStringsLoader } from '@anticrm/platform' import { presentationId } from './plugin' - +export { presentationId } export * from './utils' export * from './attributes' +export * from './types' export { default as UserBox } from './components/UserBox.svelte' export { default as UserInfo } from './components/UserInfo.svelte' diff --git a/packages/presentation/src/plugin.ts b/packages/presentation/src/plugin.ts index 55620862d1..f1acb7da1a 100644 --- a/packages/presentation/src/plugin.ts +++ b/packages/presentation/src/plugin.ts @@ -1,21 +1,23 @@ // // Copyright © 2020, 2021 Anticrm Platform Contributors. // Copyright © 2021 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 { Class, Ref } from '@anticrm/core' import type { IntlString, Plugin } from '@anticrm/platform' import { plugin } from '@anticrm/platform' +import { ObjectSearchCategory } from '.' /** * @public @@ -23,6 +25,9 @@ import { plugin } from '@anticrm/platform' export const presentationId = 'presentation' as Plugin export default plugin(presentationId, { + class: { + ObjectSearchCategory: '' as Ref> + }, string: { Create: '' as IntlString, Cancel: '' as IntlString, @@ -34,4 +39,4 @@ export default plugin(presentationId, { Deselect: '' as IntlString, AddSocialLinks: '' as IntlString } -}) \ No newline at end of file +}) diff --git a/packages/presentation/src/types.ts b/packages/presentation/src/types.ts new file mode 100644 index 0000000000..d9fe2a099b --- /dev/null +++ b/packages/presentation/src/types.ts @@ -0,0 +1,31 @@ +import { Client, Doc } from '@anticrm/core' +import { Asset, IntlString, Resource } from '@anticrm/platform' +import { AnySvelteComponent } from '@anticrm/ui' + +/** + * @public + */ +export interface ObjectSearchResult { + doc: Doc + component?: AnySvelteComponent + componentProps?: any + title: string + icon?: Asset | AnySvelteComponent + iconProps?: any +} + +/** + * @public + */ +export type ObjectSearchFactory = (client: Client, query: string) => Promise + +/** + * @public + */ +export interface ObjectSearchCategory extends Doc { + label: IntlString + icon: Asset + + // Query for documents with pattern + query: Resource +} diff --git a/packages/text-editor/lang/en.json b/packages/text-editor/lang/en.json new file mode 100644 index 0000000000..24658a9c66 --- /dev/null +++ b/packages/text-editor/lang/en.json @@ -0,0 +1,5 @@ +{ + "string": { + "Suggested": "SUGGESTED" + } +} diff --git a/packages/text-editor/package.json b/packages/text-editor/package.json index 8ab4638038..8f47932a9d 100644 --- a/packages/text-editor/package.json +++ b/packages/text-editor/package.json @@ -34,6 +34,7 @@ "svelte": "^3.37.0", "@anticrm/presentation": "~0.6.2", "@anticrm/contact": "~0.6.2", + "@anticrm/platform": "~0.6.5", "@anticrm/core": "~0.6.11", "@anticrm/ui": "~0.6.0", "@tiptap/core": "~2.0.0-beta.93", diff --git a/packages/text-editor/src/components/MentionList.svelte b/packages/text-editor/src/components/MentionList.svelte index 7f623ebbf3..07f308b26f 100644 --- a/packages/text-editor/src/components/MentionList.svelte +++ b/packages/text-editor/src/components/MentionList.svelte @@ -14,19 +14,29 @@ // limitations under the License. -->
-
-
Contacts
-
+
+
+ {#each categories as c} +
+ { + category = c + onCategory(c) + updateItems(c, query) + } }/> +
+ {/each} +
+
+ updateItems(category, query) } placeholder={placeholder} /> +
+