mirror of
https://github.com/hcengineering/platform.git
synced 2025-01-03 08:57:14 +03:00
parent
f7e220d0f2
commit
f91403e7a4
models
board/src
calendar/src
chunter/src
contact/src
document/src
gmail/src
hr/src
inventory/src
lead/src
recruit/src
task/src
telegram/src
tracker/src
packages
plugins
activity-resources/src/components
bitrix-resources/src/components/mappings
bitrix
tags-resources/src
components
CategoryBar.svelteEditTagElement.svelteLabelsPresenter.svelteTagItem.svelteTagReferencePresenter.svelteTagsAttributeEditor.svelteTagsEditor.svelteTagsFilter.svelteTagsView.svelteWeightPopup.svelte
utils.tsview-resources/src/components/filter
view/src
tests/sanity/tests
@ -89,7 +89,7 @@ export class TCard extends TTask implements Card {
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
comments?: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeRef(contact.class.Employee), board.string.Assignee)
|
||||
|
@ -62,7 +62,7 @@ export class TEvent extends TAttachedDoc implements Event {
|
||||
@Index(IndexKind.FullText)
|
||||
description!: Markup
|
||||
|
||||
@Prop(TypeString(), calendar.string.Location, calendar.icon.Location)
|
||||
@Prop(TypeString(), calendar.string.Location, { icon: calendar.icon.Location })
|
||||
@Index(IndexKind.FullText)
|
||||
location?: string
|
||||
|
||||
@ -72,7 +72,7 @@ export class TEvent extends TAttachedDoc implements Event {
|
||||
@Prop(TypeDate(true), calendar.string.DueTo)
|
||||
dueDate!: Timestamp
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
|
@ -81,7 +81,7 @@ export class TChunterMessage extends TAttachedDoc implements ChunterMessage {
|
||||
@Index(IndexKind.FullText)
|
||||
content!: string
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeRef(core.class.Account), chunter.string.CreateBy)
|
||||
@ -138,7 +138,7 @@ export class TComment extends TAttachedDoc implements Comment {
|
||||
@Index(IndexKind.FullText)
|
||||
message!: string
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
}
|
||||
|
||||
|
@ -85,7 +85,7 @@ export class TContact extends TDoc implements Contact {
|
||||
@Prop(Collection(contact.class.Channel), contact.string.ContactInfo)
|
||||
channels?: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
|
@ -89,7 +89,7 @@ export class TDocumentVersion extends TAttachedDoc implements DocumentVersion {
|
||||
@Hidden()
|
||||
content!: Markup
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments!: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
@ -116,7 +116,7 @@ export class TDocument extends TDoc implements Document {
|
||||
@Hidden()
|
||||
latest!: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
|
@ -78,7 +78,7 @@ export class TMessage extends TAttachedDoc implements Message {
|
||||
@Prop(TypeBoolean(), gmail.string.Incoming)
|
||||
incoming!: boolean
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeTimestamp(), core.string.Modified)
|
||||
@ -109,7 +109,7 @@ export class TNewMessage extends TDoc implements NewMessage {
|
||||
@Prop(ArrOf(TypeString()), gmail.string.Copy)
|
||||
copy?: string[]
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
}
|
||||
|
||||
|
@ -57,7 +57,7 @@ export class TDepartment extends TSpace implements Department {
|
||||
@Prop(Collection(contact.class.Channel), contact.string.ContactInfo)
|
||||
channels?: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
@ -131,7 +131,7 @@ export class TRequest extends TAttachedDoc implements Request {
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
comments?: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeMarkup(), core.string.Description)
|
||||
|
@ -51,7 +51,7 @@ export class TProduct extends TAttachedDoc implements Product {
|
||||
@Prop(Collection(inventory.class.Variant), inventory.string.Variants)
|
||||
variants?: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
}
|
||||
|
||||
|
@ -46,7 +46,7 @@ export class TFunnel extends TSpaceWithStates implements Funnel {
|
||||
@Index(IndexKind.FullText)
|
||||
fullDescription?: string
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
@ -66,7 +66,7 @@ export class TLead extends TTask implements Lead {
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
comments?: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeRef(contact.class.Employee), lead.string.Assignee)
|
||||
|
@ -64,7 +64,7 @@ export class TVacancy extends TSpaceWithStates implements Vacancy {
|
||||
@Index(IndexKind.FullText)
|
||||
fullDescription?: string
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeDate(), recruit.string.Due, recruit.icon.Calendar)
|
||||
@ -74,7 +74,7 @@ export class TVacancy extends TSpaceWithStates implements Vacancy {
|
||||
@Index(IndexKind.FullText)
|
||||
location?: string
|
||||
|
||||
@Prop(TypeRef(contact.class.Organization), recruit.string.Company, contact.icon.Company)
|
||||
@Prop(TypeRef(contact.class.Organization), recruit.string.Company, { icon: contact.icon.Company })
|
||||
company?: Ref<Organization>
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
@ -95,7 +95,9 @@ export class TCandidate extends TPerson implements Candidate {
|
||||
@Index(IndexKind.FullText)
|
||||
title?: string
|
||||
|
||||
@Prop(Collection(recruit.class.Applicant), recruit.string.Applications, undefined, recruit.string.ApplicationsShort)
|
||||
@Prop(Collection(recruit.class.Applicant), recruit.string.Applications, {
|
||||
shortLabel: recruit.string.ApplicationsShort
|
||||
})
|
||||
applications?: number
|
||||
|
||||
@Prop(TypeBoolean(), recruit.string.Onsite)
|
||||
@ -108,7 +110,10 @@ export class TCandidate extends TPerson implements Candidate {
|
||||
@Index(IndexKind.FullText)
|
||||
source?: string
|
||||
|
||||
@Prop(Collection(tags.class.TagReference, recruit.string.SkillLabel), recruit.string.SkillsLabel, recruit.icon.Skills)
|
||||
@Prop(Collection(tags.class.TagReference, recruit.string.SkillLabel), recruit.string.SkillsLabel, {
|
||||
icon: recruit.icon.Skills,
|
||||
schema: '3'
|
||||
})
|
||||
skills?: number
|
||||
|
||||
@Prop(Collection(recruit.class.Review, recruit.string.Review), recruit.string.Reviews)
|
||||
@ -141,7 +146,7 @@ export class TApplicant extends TTask implements Applicant {
|
||||
@Index(IndexKind.Indexed)
|
||||
declare space: Ref<Vacancy>
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
|
@ -24,7 +24,7 @@ export class TReview extends TEvent implements Review {
|
||||
@Index(IndexKind.FullText)
|
||||
verdict!: string
|
||||
|
||||
@Prop(TypeRef(contact.class.Organization), recruit.string.Company, contact.icon.Company)
|
||||
@Prop(TypeRef(contact.class.Organization), recruit.string.Company, { icon: contact.icon.Company })
|
||||
company?: Ref<Organization>
|
||||
|
||||
@Prop(Collection(recruit.class.Opinion), recruit.string.Opinions)
|
||||
@ -41,7 +41,7 @@ export class TOpinion extends TAttachedDoc implements Opinion {
|
||||
@Prop(TypeRef(recruit.class.Review), recruit.string.Review)
|
||||
declare attachedTo: Ref<Review>
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
|
@ -189,7 +189,7 @@ export class TIssue extends TTask implements Issue {
|
||||
@Prop(Collection(chunter.class.Comment), task.string.TaskComments)
|
||||
comments!: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments!: number
|
||||
|
||||
@Prop(TypeRef(contact.class.Employee), task.string.TaskAssignee)
|
||||
|
@ -58,7 +58,7 @@ export class TTelegramMessage extends TAttachedDoc implements TelegramMessage {
|
||||
@Prop(TypeBoolean(), telegram.string.Incoming)
|
||||
incoming!: boolean
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeTimestamp(), core.string.Modified)
|
||||
@ -74,7 +74,7 @@ export class TNewTelegramMessage extends TAttachedDoc implements NewTelegramMess
|
||||
@Prop(TypeString(), telegram.string.Status)
|
||||
status!: 'new' | 'sent'
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
}
|
||||
|
||||
|
@ -393,7 +393,7 @@ export class TProject extends TDoc implements Project {
|
||||
@Prop(Collection(tracker.class.Document), tracker.string.Document)
|
||||
documents!: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeDate(true), tracker.string.StartDate)
|
||||
@ -430,7 +430,7 @@ export class TSprint extends TDoc implements Sprint {
|
||||
@Prop(Collection(chunter.class.Comment), chunter.string.Comments)
|
||||
comments!: number
|
||||
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, undefined, attachment.string.Files)
|
||||
@Prop(Collection(attachment.class.Attachment), attachment.string.Attachments, { shortLabel: attachment.string.Files })
|
||||
attachments?: number
|
||||
|
||||
@Prop(TypeDate(false), tracker.string.StartDate)
|
||||
|
@ -114,6 +114,9 @@ export interface Attribute<T extends PropertyType> extends Doc, UXObject {
|
||||
index?: IndexKind
|
||||
shortLabel?: IntlString
|
||||
isCustom?: boolean
|
||||
|
||||
// Extra customization properties
|
||||
[key: string]: any
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -120,7 +120,7 @@ function getAttrs (target: any, prop: string): Record<string, any> {
|
||||
* @param icon -
|
||||
* @returns
|
||||
*/
|
||||
export function Prop (type: Type<PropertyType>, label: IntlString, icon?: Asset, shortLabel?: IntlString) {
|
||||
export function Prop (type: Type<PropertyType>, label: IntlString, extra: Partial<Attribute<PropertyType>> = {}) {
|
||||
return function (target: any, propertyKey: string): void {
|
||||
const txes = getTxes(target)
|
||||
const tx: TxCreateDoc<Attribute<PropertyType>> = {
|
||||
@ -133,12 +133,11 @@ export function Prop (type: Type<PropertyType>, label: IntlString, icon?: Asset,
|
||||
objectId: propertyKey as Ref<Attribute<PropertyType>>,
|
||||
objectClass: core.class.Attribute,
|
||||
attributes: {
|
||||
...extra,
|
||||
name: propertyKey,
|
||||
index: getIndex(target, propertyKey),
|
||||
type,
|
||||
label,
|
||||
icon,
|
||||
shortLabel,
|
||||
attributeOf: txes._id, // undefined, need to fix later
|
||||
...getAttrs(target, propertyKey)
|
||||
}
|
||||
|
@ -35,8 +35,8 @@
|
||||
import { getActions, ObjectPresenter } from '@hcengineering/view-resources'
|
||||
import { ActivityKey, DisplayTx } from '../activity'
|
||||
import activity from '../plugin'
|
||||
import TxViewTx from './TxViewTx.svelte'
|
||||
import { getValue, TxDisplayViewlet, updateViewlet } from '../utils'
|
||||
import TxViewTx from './TxViewTx.svelte'
|
||||
|
||||
export let tx: DisplayTx
|
||||
export let viewlets: Map<ActivityKey, TxViewlet>
|
||||
@ -70,7 +70,7 @@
|
||||
const query = createQuery()
|
||||
|
||||
function getProps (props: any, edit: boolean): any {
|
||||
return { ...props, edit }
|
||||
return { ...props, edit, attr: tx.collectionAttribute }
|
||||
}
|
||||
|
||||
$: updateViewlet(client, viewlets, tx).then((result) => {
|
||||
|
@ -12,7 +12,7 @@
|
||||
import { getClient } from '@hcengineering/presentation'
|
||||
|
||||
import contact, { ChannelProvider } from '@hcengineering/contact'
|
||||
import { Button, DropdownLabelsIntl, IconAdd, IconDelete } from '@hcengineering/ui'
|
||||
import { Button, DropdownLabelsIntl, EditBox, IconAdd, IconDelete } from '@hcengineering/ui'
|
||||
import DropdownLabels from '@hcengineering/ui/src/components/DropdownLabels.svelte'
|
||||
import bitrix from '../../plugin'
|
||||
|
||||
@ -72,6 +72,8 @@
|
||||
bind:selected={p.provider}
|
||||
/>
|
||||
<DropdownLabels minW0={false} label={bitrix.string.FieldMapping} {items} bind:selected={p.field} />
|
||||
<EditBox bind:value={p.include} placeholder={getEmbeddedLabel('should...')} />
|
||||
<EditBox bind:value={p.exclude} placeholder={getEmbeddedLabel('not...')} />
|
||||
|
||||
<div class="ml-1">
|
||||
<Button
|
||||
|
@ -21,6 +21,12 @@
|
||||
->
|
||||
{#if mapping.bitrixFields}
|
||||
{p.field ? mapping.bitrixFields[p.field]?.formLabel ?? mapping.bitrixFields[p.field]?.title : p.field ?? ''}
|
||||
{#if p.include !== undefined && p.include !== ''}
|
||||
/{p.include}/gi
|
||||
{/if}
|
||||
{#if p.exclude !== undefined && p.exclude !== ''}
|
||||
^/{p.exclude}/gi
|
||||
{/if}
|
||||
{/if}
|
||||
</div>
|
||||
{/each}
|
||||
|
@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@hcengineering/bitrix",
|
||||
"version": "0.6.4",
|
||||
"version": "0.6.10",
|
||||
"main": "lib/index.js",
|
||||
"author": "Anticrm Platform Contributors",
|
||||
"license": "EPL-2.0",
|
||||
|
@ -19,7 +19,14 @@ import core, {
|
||||
import tags, { TagElement } from '@hcengineering/tags'
|
||||
import { deepEqual } from 'fast-equals'
|
||||
import { BitrixClient } from './client'
|
||||
import { BitrixEntityMapping, BitrixEntityType, BitrixFieldMapping, BitrixSyncDoc, LoginInfo } from './types'
|
||||
import {
|
||||
BitrixActivity,
|
||||
BitrixEntityMapping,
|
||||
BitrixEntityType,
|
||||
BitrixFieldMapping,
|
||||
BitrixSyncDoc,
|
||||
LoginInfo
|
||||
} from './types'
|
||||
import { convert, ConvertResult } from './utils'
|
||||
import bitrix from './index'
|
||||
|
||||
@ -293,6 +300,7 @@ export async function performSynchronization (ops: {
|
||||
frontUrl: string
|
||||
loginInfo: LoginInfo
|
||||
monitor: (total: number) => void
|
||||
blobProvider?: (blobRef: any) => Promise<Blob | undefined>
|
||||
}): Promise<void> {
|
||||
const commentFields = await ops.bitrixClient.call(BitrixEntityType.Comment + '.fields', {})
|
||||
|
||||
@ -352,7 +360,6 @@ export async function performSynchronization (ops: {
|
||||
|
||||
const extraDocs: Doc[] = []
|
||||
|
||||
const convertResults: ConvertResult[] = []
|
||||
const fields = ops.mapping.$lookup?.fields as BitrixFieldMapping[]
|
||||
|
||||
const toProcess = result.result as any[]
|
||||
@ -374,7 +381,9 @@ export async function performSynchronization (ops: {
|
||||
})
|
||||
let synchronized = 0
|
||||
while (toProcess.length > 0) {
|
||||
console.log('LOAD:', synchronized, toProcess.length)
|
||||
const convertResults: ConvertResult[] = []
|
||||
|
||||
console.log('LOAD:', synchronized, added)
|
||||
synchronized++
|
||||
const [r] = toProcess.slice(0, 1)
|
||||
// Convert documents.
|
||||
@ -389,7 +398,8 @@ export async function performSynchronization (ops: {
|
||||
tagElements,
|
||||
userList,
|
||||
existingDocuments,
|
||||
defaultCategories
|
||||
defaultCategories,
|
||||
ops.blobProvider
|
||||
)
|
||||
if (ops.mapping.comments) {
|
||||
res.comments = await ops.bitrixClient
|
||||
@ -419,15 +429,48 @@ export async function performSynchronization (ops: {
|
||||
return c
|
||||
})
|
||||
})
|
||||
const communications = await ops.bitrixClient.call('crm.activity.list', {
|
||||
order: { ID: 'DESC' },
|
||||
filter: {
|
||||
OWNER_ID: res.document.bitrixId
|
||||
},
|
||||
select: ['*', 'COMMUNICATIONS']
|
||||
})
|
||||
const cr = Array.isArray(communications.result)
|
||||
? (communications.result as BitrixActivity[])
|
||||
: [communications.result as BitrixActivity]
|
||||
for (const comm of cr) {
|
||||
const c: Comment & { bitrixId: string, type: string } = {
|
||||
_id: generateId(),
|
||||
_class: chunter.class.Comment,
|
||||
message: `e-mail:<br/>
|
||||
Subject: ${comm.SUBJECT}
|
||||
${comm.DESCRIPTION}`,
|
||||
bitrixId: comm.ID,
|
||||
type: 'email',
|
||||
attachedTo: res.document._id,
|
||||
attachedToClass: res.document._class,
|
||||
collection: 'comments',
|
||||
space: res.document.space,
|
||||
modifiedBy: userList.get(comm.AUTHOR_ID) ?? core.account.System,
|
||||
modifiedOn: new Date(comm.CREATED ?? new Date().toString()).getTime()
|
||||
}
|
||||
res.comments?.push(c)
|
||||
}
|
||||
}
|
||||
|
||||
convertResults.push(res)
|
||||
extraDocs.push(...res.extraDocs)
|
||||
added++
|
||||
const total = result.total
|
||||
await syncPlatform(ops.client, ops.mapping, convertResults, ops.loginInfo, ops.frontUrl, () => {
|
||||
ops.monitor?.(total)
|
||||
})
|
||||
if (added >= ops.limit) {
|
||||
break
|
||||
}
|
||||
} catch (err: any) {
|
||||
console.log('failed to obtain data for', r)
|
||||
console.log('failed to obtain data for', r, err)
|
||||
await new Promise((resolve) => {
|
||||
// Sleep for a while
|
||||
setTimeout(resolve, 1000)
|
||||
@ -435,10 +478,6 @@ export async function performSynchronization (ops: {
|
||||
}
|
||||
toProcess.splice(0, 1)
|
||||
}
|
||||
const total = result.total
|
||||
await syncPlatform(ops.client, ops.mapping, convertResults, ops.loginInfo, ops.frontUrl, () => {
|
||||
ops.monitor?.(total)
|
||||
})
|
||||
|
||||
processed = result.next
|
||||
}
|
||||
|
@ -202,6 +202,8 @@ export interface CreateTagOperation {
|
||||
export interface ChannelFieldMapping {
|
||||
provider: Ref<ChannelProvider>
|
||||
field: string
|
||||
include?: string // Regexp pattern to match value.
|
||||
exclude?: string // Regexp pattern to match value.
|
||||
}
|
||||
|
||||
/**
|
||||
@ -230,3 +232,14 @@ export interface BitrixFieldMapping extends AttachedDoc {
|
||||
|
||||
operation: CopyValueOperation | CreateTagOperation | CreateChannelOperation | DownloadAttachmentOperation
|
||||
}
|
||||
|
||||
/**
|
||||
* @public
|
||||
*/
|
||||
export interface BitrixActivity {
|
||||
ID: string
|
||||
SUBJECT: string
|
||||
DESCRIPTION: string
|
||||
AUTHOR_ID: string
|
||||
CREATED: number
|
||||
}
|
||||
|
@ -183,6 +183,15 @@ export async function convert (
|
||||
if (lval != null && lval !== '') {
|
||||
const vals = Array.isArray(lval) ? lval : [lval]
|
||||
for (const llVal of vals) {
|
||||
const svalue = typeof llVal === 'string' ? llVal : `${JSON.stringify(llVal)}`
|
||||
if (f.include != null || f.exclude != null) {
|
||||
if (f.include !== undefined && svalue.match(f.include) == null) {
|
||||
continue
|
||||
}
|
||||
if (f.exclude !== undefined && svalue.match(f.exclude) != null) {
|
||||
continue
|
||||
}
|
||||
}
|
||||
const c: Channel = {
|
||||
_id: generateId(),
|
||||
_class: contact.class.Channel,
|
||||
@ -190,7 +199,7 @@ export async function convert (
|
||||
attachedToClass: attr.attributeOf,
|
||||
collection: attr.name,
|
||||
modifiedBy: document.modifiedBy,
|
||||
value: llVal,
|
||||
value: svalue,
|
||||
provider: f.provider,
|
||||
space: document.space,
|
||||
modifiedOn: document.modifiedOn
|
||||
|
@ -169,10 +169,11 @@
|
||||
<div class="flex-row-center caption-color states">
|
||||
<div class="antiStatesBar mask-none {stepStyle}">
|
||||
{#each visibleCategories as item, i}
|
||||
<!-- svelte-ignore a11y-click-events-have-key-events -->
|
||||
<div
|
||||
bind:this={visibleCategoriesRef[i]}
|
||||
class="categoryElement flex-center"
|
||||
label={item.label}
|
||||
id={item.label}
|
||||
style={getTagStyle(getPlatformColorForText(item.label), item._id === category)}
|
||||
on:click={(evt) => {
|
||||
if (mode === 'category') {
|
||||
|
@ -102,6 +102,7 @@
|
||||
<div class="flex-row-center">
|
||||
<div class="flex-col">
|
||||
<div class="fs-title flex-row-center">
|
||||
<!-- svelte-ignore a11y-click-events-have-key-events -->
|
||||
<div
|
||||
class="color"
|
||||
style={getTagStyle(getPlatformColor(data.color))}
|
||||
|
@ -38,6 +38,7 @@
|
||||
})
|
||||
</script>
|
||||
|
||||
<!-- svelte-ignore a11y-click-events-have-key-events -->
|
||||
<div
|
||||
class="labels-container"
|
||||
style:justify-content={kind === 'short' ? 'space-between' : 'flex-start'}
|
||||
@ -52,7 +53,7 @@
|
||||
>
|
||||
{#each items as value, i}
|
||||
<div class="label-box wrap-{kind}">
|
||||
<TagReferencePresenter {value} kind={'kanban-labels'} bind:realWidth={widths[i]} />
|
||||
<TagReferencePresenter attr={undefined} {value} kind={'kanban-labels'} bind:realWidth={widths[i]} />
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
|
@ -24,12 +24,13 @@
|
||||
export let element: TagElement | undefined = undefined
|
||||
export let action: Asset | AnySvelteComponent | undefined = undefined
|
||||
export let selected: boolean = false
|
||||
export let schema: '0' | '3' | '9' = '9'
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
$: name = element?.title ?? tag?.title ?? 'New item'
|
||||
|
||||
$: tagIcon = tagLevel[(((tag?.weight ?? 0) % 3) + 1) as 1 | 2 | 3]
|
||||
$: tagIcon = schema === '3' ? undefined : tagLevel[(((tag?.weight ?? 0) % 3) + 1) as 1 | 2 | 3]
|
||||
</script>
|
||||
|
||||
<div
|
||||
@ -45,7 +46,7 @@
|
||||
>
|
||||
{name}
|
||||
<span class="ml-1">
|
||||
{#if tag}
|
||||
{#if tag && tagIcon && schema !== '0'}
|
||||
<Icon icon={tagIcon} size={'small'} />
|
||||
{/if}
|
||||
</span>
|
||||
|
@ -13,6 +13,7 @@
|
||||
// limitations under the License.
|
||||
-->
|
||||
<script lang="ts">
|
||||
import { AnyAttribute } from '@hcengineering/core'
|
||||
import type { TagReference } from '@hcengineering/tags'
|
||||
import { getPlatformColor, Icon, IconClose, resizeObserver } from '@hcengineering/ui'
|
||||
import { createEventDispatcher } from 'svelte'
|
||||
@ -23,6 +24,7 @@
|
||||
export let isEditable: boolean = false
|
||||
export let kind: 'labels' | 'kanban-labels' | 'skills' = 'skills'
|
||||
export let realWidth: number | undefined = undefined
|
||||
export let attr: AnyAttribute | undefined
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
$: tagIcon = tagLevel[(((value?.weight ?? 0) % 3) + 1) as 1 | 2 | 3]
|
||||
@ -30,7 +32,7 @@
|
||||
|
||||
{#if value}
|
||||
{#if kind === 'skills'}
|
||||
<TagItem tag={value} />
|
||||
<TagItem tag={value} schema={attr?.schema ?? '0'} />
|
||||
{:else if kind === 'kanban-labels'}
|
||||
<button
|
||||
class="label-container"
|
||||
|
@ -1,6 +1,6 @@
|
||||
<script lang="ts">
|
||||
import { IntlString } from '@hcengineering/platform'
|
||||
import { Doc, Ref } from '@hcengineering/core'
|
||||
import { AnyAttribute, Doc, Ref } from '@hcengineering/core'
|
||||
import { createQuery, getClient } from '@hcengineering/presentation'
|
||||
import type { TagReference, TagElement } from '@hcengineering/tags'
|
||||
import tags from '@hcengineering/tags'
|
||||
@ -11,6 +11,7 @@
|
||||
export let object: Doc
|
||||
export let label: IntlString
|
||||
export let isEditable: boolean = true
|
||||
export let attr: AnyAttribute | undefined = undefined
|
||||
|
||||
let items: TagReference[] = []
|
||||
const query = createQuery()
|
||||
@ -33,7 +34,7 @@
|
||||
<div class="flex-row-center flex-wrap">
|
||||
{#each items as value}
|
||||
<div class="step-container">
|
||||
<TagReferencePresenter {value} {isEditable} kind={'labels'} on:remove={(res) => removeTag(res.detail)} />
|
||||
<TagReferencePresenter {attr} {value} {isEditable} kind={'labels'} on:remove={(res) => removeTag(res.detail)} />
|
||||
</div>
|
||||
{/each}
|
||||
{#if isEditable}
|
||||
|
@ -37,6 +37,7 @@
|
||||
export let key: KeyedAttribute
|
||||
export let showTitle = true
|
||||
export let elements: Map<Ref<TagElement>, TagElement>
|
||||
export let schema: '3' | '9' = key.attr.schema ?? '9'
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
@ -131,6 +132,7 @@
|
||||
<TagItem
|
||||
{tag}
|
||||
element={elements.get(tag.tag)}
|
||||
{schema}
|
||||
action={IconClose}
|
||||
on:action={() => {
|
||||
removeTag(tag._id)
|
||||
@ -138,7 +140,7 @@
|
||||
on:click={(evt) => {
|
||||
showPopup(
|
||||
WeightPopup,
|
||||
{ value: tag.weight ?? 1, format: 'number' },
|
||||
{ value: tag.weight ?? 1, format: 'number', schema },
|
||||
getEventPopupPositionElement(evt),
|
||||
(res) => {
|
||||
if (Number.isFinite(res) && res >= 0 && res <= 8) {
|
||||
|
@ -20,13 +20,13 @@
|
||||
import {
|
||||
Button,
|
||||
CheckBox,
|
||||
deviceOptionsStore,
|
||||
getEventPopupPositionElement,
|
||||
getPlatformColor,
|
||||
Label,
|
||||
Loading,
|
||||
resizeObserver,
|
||||
showPopup,
|
||||
deviceOptionsStore
|
||||
showPopup
|
||||
} from '@hcengineering/ui'
|
||||
import { Filter } from '@hcengineering/view'
|
||||
import { FilterQuery } from '@hcengineering/view-resources'
|
||||
@ -111,10 +111,12 @@
|
||||
categories = categories
|
||||
}
|
||||
|
||||
$: schema = filter.key.attribute.schema ?? '9'
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
getValues(search)
|
||||
|
||||
$: tagLevelIcon = tagLevel[((level % 3) + 1) as 1 | 2 | 3]
|
||||
$: tagLevelIcon = schema === '3' ? undefined : tagLevel[((level % 3) + 1) as 1 | 2 | 3]
|
||||
$: tagLevelLabel = [tags.string.Initial, tags.string.Meaningfull, tags.string.Expert][Math.floor(level / 3)]
|
||||
</script>
|
||||
|
||||
@ -135,7 +137,7 @@
|
||||
label={tagLevelLabel}
|
||||
icon={tagLevelIcon}
|
||||
on:click={(evt) => {
|
||||
showPopup(WeightPopup, { value: level }, getEventPopupPositionElement(evt), (res) => {
|
||||
showPopup(WeightPopup, { value: level, schema }, getEventPopupPositionElement(evt), (res) => {
|
||||
if (Number.isFinite(res) && res >= 0 && res <= 8) {
|
||||
if (res != null) {
|
||||
level = res
|
||||
|
@ -126,16 +126,12 @@
|
||||
props: { edit: true, keyTitle },
|
||||
sortingKey: 'title'
|
||||
},
|
||||
...(category === undefined
|
||||
? [
|
||||
{
|
||||
key: '$lookup.category',
|
||||
presenter: tags.component.CategoryPresenter,
|
||||
sortingKey: 'category',
|
||||
label: tags.string.CategoryLabel
|
||||
}
|
||||
]
|
||||
: []),
|
||||
{
|
||||
key: '$lookup.category',
|
||||
presenter: tags.component.CategoryPresenter,
|
||||
sortingKey: 'category',
|
||||
label: tags.string.CategoryLabel
|
||||
},
|
||||
{
|
||||
key: '',
|
||||
presenter: tags.component.TagElementCountPresenter,
|
||||
|
@ -19,6 +19,7 @@
|
||||
import { tagLevel } from '../utils'
|
||||
|
||||
export let value: number | undefined
|
||||
export let schema: '3' | '9' = '9'
|
||||
|
||||
const dispatch = createEventDispatcher()
|
||||
|
||||
@ -29,18 +30,30 @@
|
||||
<div class="header no-border p-3">
|
||||
{#each labels as l, i}
|
||||
<div class="flex gap-2 p-1">
|
||||
{#each Object.entries(tagLevel) as k, j}
|
||||
{@const valueK = i * 3 + j}
|
||||
{#if schema === '9'}
|
||||
{#each Object.entries(tagLevel) as k, j}
|
||||
{@const valueK = i * 3 + j}
|
||||
<Button
|
||||
label={l}
|
||||
icon={k[1]}
|
||||
size={'small'}
|
||||
justify={'left'}
|
||||
selected={value === valueK}
|
||||
on:click={() => dispatch('close', valueK)}
|
||||
width={'8rem'}
|
||||
/>
|
||||
{/each}
|
||||
{:else}
|
||||
{@const valueK = i * 3}
|
||||
<Button
|
||||
label={l}
|
||||
icon={k[1]}
|
||||
size={'small'}
|
||||
justify={'left'}
|
||||
selected={value === valueK}
|
||||
on:click={() => dispatch('close', valueK)}
|
||||
width={'8rem'}
|
||||
/>
|
||||
{/each}
|
||||
{/if}
|
||||
</div>
|
||||
{/each}
|
||||
</div>
|
||||
|
@ -38,8 +38,9 @@ export async function getRefs (filter: Filter, onUpdate: () => void): Promise<Ar
|
||||
return await promise
|
||||
}
|
||||
|
||||
export const tagLevel: Record<1 | 2 | 3, Asset> = {
|
||||
export const tagLevel: Record<0 | 1 | 2 | 3, Asset> = {
|
||||
3: tags.icon.Level3,
|
||||
2: tags.icon.Level2,
|
||||
1: tags.icon.Level1
|
||||
1: tags.icon.Level1,
|
||||
0: tags.icon.Tags
|
||||
}
|
||||
|
@ -81,6 +81,7 @@
|
||||
return {
|
||||
_class,
|
||||
key: isCollection ? '_id' : key,
|
||||
attribute,
|
||||
label: attribute.label,
|
||||
icon: attribute.icon ?? clazz.icon ?? attrOf.icon ?? view.icon.Setting,
|
||||
component: filter.component
|
||||
|
@ -47,6 +47,7 @@ import type {
|
||||
export interface KeyFilter {
|
||||
_class: Ref<Class<Doc>>
|
||||
key: string
|
||||
attribute: AnyAttribute
|
||||
component: AnyComponent
|
||||
label: IntlString
|
||||
icon: Asset | AnySvelteComponent | undefined
|
||||
|
@ -31,7 +31,7 @@ test.describe('workbench tests', () => {
|
||||
await expect(page).toHaveURL(`${PlatformURI}/workbench/sanity-ws/recruit/vacancies`)
|
||||
// Click text=Software Engineer
|
||||
await page.click('text=Software Engineer')
|
||||
await expect(page.locator('text=Software Engineer')).toBeVisible()
|
||||
await expect(page.locator('text=Software Engineer')).toBeDefined()
|
||||
await expect(page.locator('text="APP-1"')).toBeDefined()
|
||||
// await page.click('[name="tooltip-task:string:Kanban"]')
|
||||
await page.click('.tablist-container div:nth-child(2)')
|
||||
|
Loading…
Reference in New Issue
Block a user