mirror of
https://github.com/hcengineering/platform.git
synced 2026-08-17 18:05:42 +02:00
254 lines
8.3 KiB
Svelte
254 lines
8.3 KiB
Svelte
<!--
|
|
// Copyright © 2023 Hardcore Engineering Inc.
|
|
//
|
|
// Licensed under the Eclipse Public License, Version 2.0 (the "License");
|
|
// you may not use this file except in compliance with the License. You may
|
|
// obtain a copy of the License at https://www.eclipse.org/legal/epl-2.0
|
|
//
|
|
// Unless required by applicable law or agreed to in writing, software
|
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
//
|
|
// See the License for the specific language governing permissions and
|
|
// limitations under the License.
|
|
-->
|
|
<script lang="ts">
|
|
import activity, {
|
|
ActivityMessage,
|
|
ActivityMessageViewType,
|
|
DisplayActivityMessage,
|
|
DisplayDocUpdateMessage,
|
|
DocUpdateMessage,
|
|
DocUpdateMessageViewlet
|
|
} from '@hcengineering/activity'
|
|
import { Person, PersonAccount } from '@hcengineering/contact'
|
|
import { personAccountByIdStore, personByIdStore } from '@hcengineering/contact-resources'
|
|
import { Account, AttachedDoc, Class, Collection, Doc, Ref, Space } from '@hcengineering/core'
|
|
import { IntlString } from '@hcengineering/platform'
|
|
import { createQuery, getClient } from '@hcengineering/presentation'
|
|
import { Action, Component, ShowMore } from '@hcengineering/ui'
|
|
import { AttributeModel } from '@hcengineering/view'
|
|
import { buildRemovedDoc, checkIsObjectRemoved } from '@hcengineering/view-resources'
|
|
|
|
import ActivityMessageTemplate from '../activity-message/ActivityMessageTemplate.svelte'
|
|
import DocUpdateMessageAttributes from './DocUpdateMessageAttributes.svelte'
|
|
import DocUpdateMessageContent from './DocUpdateMessageContent.svelte'
|
|
import DocUpdateMessageHeader from './DocUpdateMessageHeader.svelte'
|
|
|
|
import { getAttributeModel, getCollectionAttribute } from '../../activityMessagesUtils'
|
|
import { getIsTextType } from '../../utils'
|
|
|
|
export let value: DisplayDocUpdateMessage
|
|
export let doc: Doc | undefined = undefined
|
|
export let showNotify: boolean = false
|
|
export let isHighlighted: boolean = false
|
|
export let isSelected: boolean = false
|
|
export let shouldScroll: boolean = false
|
|
export let embedded: boolean = false
|
|
export let withActions: boolean = true
|
|
export let showEmbedded = false
|
|
export let hideFooter = false
|
|
export let actions: Action[] = []
|
|
export let skipLabel = false
|
|
export let hoverable = true
|
|
export let hoverStyles: 'borderedHover' | 'filledHover' = 'borderedHover'
|
|
export let hideLink = false
|
|
export let type: ActivityMessageViewType = 'default'
|
|
export let readonly = false
|
|
export let space: Ref<Space> | undefined = undefined
|
|
export let onClick: (() => void) | undefined = undefined
|
|
|
|
const client = getClient()
|
|
const hierarchy = client.getHierarchy()
|
|
|
|
const objectQuery = createQuery()
|
|
const parentObjectQuery = createQuery()
|
|
|
|
let objectName: IntlString | undefined = undefined
|
|
let collectionName: IntlString | undefined = undefined
|
|
|
|
$: collectionAttribute = getCollectionAttribute(hierarchy, value.attachedToClass, value.updateCollection)
|
|
$: clazz = hierarchy.getClass(value.objectClass)
|
|
|
|
$: objectName = (collectionAttribute?.type as Collection<AttachedDoc>)?.itemLabel ?? clazz.label
|
|
$: collectionName = collectionAttribute?.label
|
|
|
|
let person: Person | undefined = undefined
|
|
let viewlet: DocUpdateMessageViewlet | undefined
|
|
let attributeModel: AttributeModel | undefined = undefined
|
|
let parentMessage: DisplayActivityMessage | undefined = undefined
|
|
let parentObject: Doc | undefined
|
|
let object: Doc | undefined
|
|
let isObjectRemoved: boolean = false
|
|
|
|
$: [viewlet] = client
|
|
.getModel()
|
|
.findAllSync(activity.class.DocUpdateMessageViewlet, { action: value.action, objectClass: value.objectClass })
|
|
|
|
$: void getAttributeModel(client, value.attributeUpdates, value.objectClass).then((model) => {
|
|
attributeModel = model
|
|
})
|
|
|
|
async function getParentMessage (
|
|
_class: Ref<Class<Doc>>,
|
|
_id: Ref<Doc>,
|
|
space: Ref<Space>
|
|
): Promise<ActivityMessage | undefined> {
|
|
if (hierarchy.isDerived(_class, activity.class.ActivityMessage)) {
|
|
return await client.findOne(activity.class.ActivityMessage, { _id: _id as Ref<ActivityMessage>, space })
|
|
}
|
|
}
|
|
|
|
$: void getParentMessage(value.attachedToClass, value.attachedTo, value.space).then((res) => {
|
|
parentMessage = res as DisplayActivityMessage
|
|
})
|
|
|
|
$: person = getPerson(value.createdBy, $personAccountByIdStore, $personByIdStore)
|
|
|
|
function getPerson (
|
|
_id: Ref<Account> | undefined,
|
|
accountById: Map<Ref<PersonAccount>, PersonAccount>,
|
|
personById: Map<Ref<Person>, Person>
|
|
): Person | undefined {
|
|
if (_id === undefined) {
|
|
return undefined
|
|
}
|
|
|
|
const personAccount = accountById.get(_id as Ref<PersonAccount>)
|
|
|
|
if (personAccount === undefined) {
|
|
return undefined
|
|
}
|
|
|
|
return personById.get(personAccount.person)
|
|
}
|
|
|
|
$: void loadObject(value.objectId, value.objectClass, doc)
|
|
$: void loadParentObject(value, parentMessage, doc)
|
|
|
|
async function loadObject (_id: Ref<Doc>, _class: Ref<Class<Doc>>, doc?: Doc): Promise<void> {
|
|
if (doc !== undefined && doc._id === _id) {
|
|
object = doc
|
|
isObjectRemoved = false
|
|
return
|
|
}
|
|
|
|
isObjectRemoved = await checkIsObjectRemoved(client, _id, _class)
|
|
|
|
if (isObjectRemoved) {
|
|
object = await buildRemovedDoc(client, _id, _class)
|
|
} else {
|
|
objectQuery.query(_class, { _id }, (res) => {
|
|
object = res[0]
|
|
})
|
|
}
|
|
}
|
|
|
|
async function loadParentObject (
|
|
message: Pick<DocUpdateMessage, 'attachedTo' | 'attachedToClass' | 'objectId' | 'space'>,
|
|
parentMessage?: Pick<ActivityMessage, 'attachedTo' | 'space' | 'attachedToClass'>,
|
|
doc?: Doc
|
|
): Promise<void> {
|
|
if (parentMessage === undefined && message.objectId === message.attachedTo) {
|
|
return
|
|
}
|
|
|
|
const _id = parentMessage !== undefined ? parentMessage.attachedTo : message.attachedTo
|
|
const _class = parentMessage !== undefined ? parentMessage.attachedToClass : message.attachedToClass
|
|
const space = parentMessage !== undefined ? parentMessage.space : message.space
|
|
|
|
if (doc !== undefined && doc._id === _id) {
|
|
parentObject = doc
|
|
return
|
|
}
|
|
|
|
const isRemoved = await checkIsObjectRemoved(client, _id, _class)
|
|
|
|
if (isRemoved) {
|
|
parentObject = await buildRemovedDoc(client, _id, _class)
|
|
return
|
|
}
|
|
|
|
parentObjectQuery.query(_class, { _id, space }, (res) => {
|
|
parentObject = res[0]
|
|
})
|
|
}
|
|
|
|
$: if (object != null && value.objectClass !== object._class) {
|
|
object = undefined
|
|
}
|
|
</script>
|
|
|
|
<ActivityMessageTemplate
|
|
message={value}
|
|
{parentMessage}
|
|
{person}
|
|
{showNotify}
|
|
{isHighlighted}
|
|
{isSelected}
|
|
{shouldScroll}
|
|
{embedded}
|
|
{withActions}
|
|
{viewlet}
|
|
{showEmbedded}
|
|
{hideFooter}
|
|
{actions}
|
|
{skipLabel}
|
|
{hoverable}
|
|
{hoverStyles}
|
|
{readonly}
|
|
type={viewlet?.label || getIsTextType(attributeModel) ? 'default' : type}
|
|
showDatePreposition={hideLink}
|
|
{onClick}
|
|
>
|
|
<svelte:fragment slot="header">
|
|
<DocUpdateMessageHeader message={value} {object} {parentObject} {viewlet} {person} {attributeModel} {hideLink} />
|
|
</svelte:fragment>
|
|
<svelte:fragment slot="content">
|
|
{#if viewlet?.component && object}
|
|
<ShowMore>
|
|
<div class="customContent">
|
|
{#each value?.previousMessages ?? [] as msg}
|
|
<Component
|
|
is={viewlet.component}
|
|
props={{ message: msg, _id: msg.objectId, _class: msg.objectClass, onClick }}
|
|
/>
|
|
{/each}
|
|
<Component
|
|
is={viewlet.component}
|
|
props={{ message: value, _id: value.objectId, _class: value.objectClass, value: object, onClick }}
|
|
/>
|
|
</div>
|
|
</ShowMore>
|
|
{:else if value.action === 'create' || value.action === 'remove'}
|
|
<ShowMore>
|
|
<DocUpdateMessageContent
|
|
message={value}
|
|
{viewlet}
|
|
{objectName}
|
|
{collectionName}
|
|
objectIcon={collectionAttribute?.icon ?? clazz.icon}
|
|
/>
|
|
</ShowMore>
|
|
{:else if value.attributeUpdates && attributeModel}
|
|
<DocUpdateMessageAttributes
|
|
attributeUpdates={value.attributeUpdates}
|
|
{attributeModel}
|
|
{viewlet}
|
|
{space}
|
|
{object}
|
|
message={value}
|
|
/>
|
|
{/if}
|
|
</svelte:fragment>
|
|
</ActivityMessageTemplate>
|
|
|
|
<style lang="scss">
|
|
.customContent {
|
|
display: flex;
|
|
flex-wrap: wrap;
|
|
column-gap: 0.625rem;
|
|
row-gap: 0.625rem;
|
|
}
|
|
</style>
|