Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion common/config/rush/pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion models/card/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,7 @@ import { PaletteColorIndexes } from '@hcengineering/ui/src/colors'
import { type AnyComponent } from '@hcengineering/ui/src/types'
import { type BuildModelKey } from '@hcengineering/view'
import { createActions } from './actions'
import { definePermissions } from './permissions'
import { defineActionPermissions, definePermissions } from './permissions'
import card from './plugin'
import notification from '@hcengineering/notification'

Expand Down Expand Up @@ -426,6 +426,7 @@ export function createModel (builder: Builder): void {

defineTabs(builder)
definePermissions(builder)
defineActionPermissions(builder)

builder.mixin(card.class.Card, core.class.Class, view.mixin.ObjectIcon, {
component: card.component.CardIcon
Expand Down
32 changes: 32 additions & 0 deletions models/card/src/permissions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -154,3 +154,35 @@ export function definePermissions (builder: Builder): void {
card.permission.ForbidRemoveCard
)
}

export function defineActionPermissions (builder: Builder): void {
builder.createDoc(
core.class.Permission,
core.space.Model,
{
label: card.string.LockSection,
txClass: core.class.TxUpdateDoc,
objectClass: card.class.Card,
txMatch: {
'operations.$push.readonlySections': { $exists: true }
},
scope: 'space'
},
card.permission.LockSection
)

builder.createDoc(
core.class.Permission,
core.space.Model,
{
label: card.string.UnLockSection,
txClass: core.class.TxUpdateDoc,
objectClass: card.class.Card,
txMatch: {
'operations.$pull.readonlySections': { $exists: true }
},
scope: 'space'
},
card.permission.UnlockSection
)
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/cs.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Karta aktualizována",
"CardCreated": "Karta vytvořena",
"MyCards": "Moje karty",
"GotoMyCards": "Přejít na moje karty"
"GotoMyCards": "Přejít na moje karty",
"LockSection": "Zamknout sekci",
"UnLockSection": "Odemknout sekci",
"SectionLocked": "Sekce {section} zamknuta",
"SectionUnlocked": "Sekce {section} odemknuta"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/de.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Karte aktualisiert",
"CardCreated": "Karte erstellt",
"MyCards": "Meine Karten",
"GotoMyCards": "Zu meinen Karten"
"GotoMyCards": "Zu meinen Karten",
"LockSection": "Sperren",
"UnLockSection": "Entsperren",
"SectionLocked": "Sektion {section} gesperrt",
"SectionUnlocked": "Sektion {section} entsperrt"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Card updated",
"CardCreated": "Card created",
"MyCards": "My cards",
"GotoMyCards": "Go to my cards"
"GotoMyCards": "Go to my cards",
"LockSection": "Lock section",
"UnLockSection": "Unlock section",
"SectionLocked": "Section {section} locked",
"SectionUnlocked": "Section {section} unlocked"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/es.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Tarjeta actualizada",
"CardCreated": "Tarjeta creada",
"MyCards": "Mis tarjetas",
"GotoMyCards": "Ir a mis tarjetas"
"GotoMyCards": "Ir a mis tarjetas",
"LockSection": "Bloquear sección",
"UnLockSection": "Desbloquear sección",
"SectionLocked": "Sección {section} bloqueada",
"SectionUnlocked": "Sección {section} desbloqueada"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/fr.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Carte mise à jour",
"CardCreated": "Carte créée",
"MyCards": "Mes cartes",
"GotoMyCards": "Aller à mes cartes"
"GotoMyCards": "Aller à mes cartes",
"LockSection": "Verrouiller la section",
"UnLockSection": "Déverrouiller la section",
"SectionLocked": "Section {section} verrouillée",
"SectionUnlocked": "Section {section} déverrouillée"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/it.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Scheda aggiornata",
"CardCreated": "Scheda creata",
"MyCards": "Le mie carte",
"GotoMyCards": "Vai alle mie carte"
"GotoMyCards": "Vai alle mie carte",
"LockSection": "Blocca sezione",
"UnLockSection": "Sblocca sezione",
"SectionLocked": "Sezione {section} bloccata",
"SectionUnlocked": "Sezione {section} sbloccata"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/ja.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "カードが更新されました",
"CardCreated": "カードが作成されました",
"MyCards": "マイカード",
"GotoMyCards": "マイカードへ移動"
"GotoMyCards": "マイカードへ移動",
"LockSection": "セクションをロック",
"UnLockSection": "セクションをアンロック",
"SectionLocked": "セクション {section} ロック済み",
"SectionUnlocked": "セクション {section} アンロック済み"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/pt-br.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Cartão atualizado",
"CardCreated": "Cartão criado",
"MyCards": "Meus cartões",
"GotoMyCards": "Ir para meus cartões"
"GotoMyCards": "Ir para meus cartões",
"LockSection": "Bloquear seção",
"UnLockSection": "Desbloquear seção",
"SectionLocked": "Seção {section} bloqueada",
"SectionUnlocked": "Seção {section} desbloqueada"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/pt.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Cartão atualizado",
"CardCreated": "Cartão criado",
"MyCards": "Meus cartões",
"GotoMyCards": "Ir para meus cartões"
"GotoMyCards": "Ir para meus cartões",
"LockSection": "Bloquear seção",
"UnLockSection": "Desbloquear seção",
"SectionLocked": "Seção {section} bloqueada",
"SectionUnlocked": "Seção {section} desbloqueada"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/ru.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Карточка обновлена",
"CardCreated": "Карточка создана",
"MyCards": "Мои карты",
"GotoMyCards": "Перейти к моим картам"
"GotoMyCards": "Перейти к моим картам",
"LockSection": "Заблокировать секцию",
"UnLockSection": "Разблокировать секцию",
"SectionLocked": "Секция {section} заблокирована",
"SectionUnlocked": "Секция {section} разблокирована"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/tr.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "Kart güncellendi",
"CardCreated": "Kart oluşturuldu",
"MyCards": "Benim kartlarım",
"GotoMyCards": "Benim kartlarıma git"
"GotoMyCards": "Benim kartlarıma git",
"LockSection": "Bölümü kilitle",
"UnLockSection": "Bölümü kilitle",
"SectionLocked": "Bölüm {section} kilitli",
"SectionUnlocked": "Bölüm {section} kilidi açıldı"
}
}
6 changes: 5 additions & 1 deletion plugins/card-assets/lang/zh.json
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,10 @@
"CardUpdated": "卡片已更新",
"CardCreated": "卡片已创建",
"MyCards": "我的卡片",
"GotoMyCards": "转到我的卡片"
"GotoMyCards": "转到我的卡片",
"LockSection": "锁定部分",
"UnLockSection": "解锁部分",
"SectionLocked": "部分 {section} 已锁定",
"SectionUnlocked": "部分 {section} 已解锁"
}
}
42 changes: 38 additions & 4 deletions plugins/card-resources/src/components/MasterTagAttributes.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,11 @@
import CardAttributes from './CardAttributes.svelte'
import { AccountRole, getCurrentAccount, hasAccountRole } from '@hcengineering/core'
import CardIcon from './CardIcon.svelte'
import { canLockSection, canUnlockSection } from '../utils'
import { permissionsStore } from '@hcengineering/contact-resources'
import Lock from './icons/Lock.svelte'
import Unlock from './icons/Unlock.svelte'
import card from '../plugin'

export let value: Card
export let readonly: boolean = false
Expand All @@ -49,6 +54,16 @@
export function expand (): void {
isCollapsed = false
}

$: isLocked = value.readonlySections?.includes(value._class) ?? false
$: canLock = canLockSection(value.space, $permissionsStore)
$: canUnlock = canUnlockSection(value.space, $permissionsStore)

async function toggleLock (ev: MouseEvent): Promise<void> {
ev.stopPropagation()
const op = isLocked ? '$pull' : '$push'
await client.update(value, { [op]: { readonlySections: value._class } })
}
</script>

<div class="header flex flex-gap-2">
Expand All @@ -57,8 +72,19 @@
<Label {label} />
<Chevron expanded={!isCollapsed} outline fill={'var(--content-color)'} />
</div>
{#if hasAccountRole(getCurrentAccount(), AccountRole.Maintainer)}
<div class="btns">
<div class="btns">
{#if (isLocked && canUnlock) || (!isLocked && canLock)}
<div class="lock-btn">
<Button
icon={isLocked ? Unlock : Lock}
kind={'link'}
size={'medium'}
showTooltip={{ label: isLocked ? card.string.UnLockSection : card.string.LockSection }}
on:click={toggleLock}
/>
</div>
{/if}
{#if hasAccountRole(getCurrentAccount(), AccountRole.Maintainer)}
<Button
icon={IconAdd}
kind={'link'}
Expand All @@ -84,8 +110,8 @@
navigate(loc)
}}
/>
</div>
{/if}
{/if}
</div>
</div>
<ExpandCollapse isExpanded={!isCollapsed}>
<CardAttributes object={value} _class={value._class} {readonly} {ignoreKeys} {fourRows} showCollaborators />
Expand Down Expand Up @@ -116,6 +142,14 @@
display: flex;
align-items: center;
visibility: hidden;

.lock-btn {
opacity: 0.5;
transition: opacity 0.2s;
&:hover {
opacity: 1;
}
}
}
}
</style>
42 changes: 38 additions & 4 deletions plugins/card-resources/src/components/TagAttributes.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,12 @@
themeStore,
tooltip
} from '@hcengineering/ui'
import { permissionsStore } from '@hcengineering/contact-resources'
import { canLockSection, canUnlockSection } from '../utils'
import CardAttributes from './CardAttributes.svelte'
import Lock from './icons/Lock.svelte'
import Unlock from './icons/Unlock.svelte'
import card from '../plugin'

export let value: Card
export let tag: Tag
Expand All @@ -54,6 +59,16 @@
$: color = getPlatformColorDef(tag.background ?? 0, $themeStore.dark).color

$: isEditable = h.hasMixin(tag, setting.mixin.Editable) && h.as(tag, setting.mixin.Editable).value

$: isLocked = value.readonlySections?.includes(tag._id) ?? false
$: canLock = canLockSection(value.space, $permissionsStore)
$: canUnlock = canUnlockSection(value.space, $permissionsStore)

async function toggleLock (ev: MouseEvent): Promise<void> {
ev.stopPropagation()
const op = isLocked ? '$pull' : '$push'
await client.update(value, { [op]: { readonlySections: tag._id } })
}
</script>

<div class="header flex flex-gap-2">
Expand All @@ -68,8 +83,19 @@
</span>
<Chevron expanded={!isCollapsed} outline fill={'var(--content-color'} />
</div>
{#if hasAccountRole(getCurrentAccount(), AccountRole.Maintainer) && isEditable}
<div class="btns">
<div class="btns">
{#if (isLocked && canUnlock) || (!isLocked && canLock)}
<div class="lock-btn">
<Button
icon={isLocked ? Unlock : Lock}
kind={'link'}
size={'medium'}
showTooltip={{ label: isLocked ? card.string.UnLockSection : card.string.LockSection }}
on:click={toggleLock}
/>
</div>
{/if}
{#if hasAccountRole(getCurrentAccount(), AccountRole.Maintainer) && isEditable}
<Button
icon={IconAdd}
kind={'link'}
Expand All @@ -95,8 +121,8 @@
navigate(loc)
}}
/>
</div>
{/if}
{/if}
</div>
</div>
<ExpandCollapse isExpanded={!isCollapsed}>
<CardAttributes object={value} _class={tag._id} to={tag.extends} {readonly} {ignoreKeys} />
Expand Down Expand Up @@ -134,6 +160,14 @@
display: flex;
align-items: center;
visibility: hidden;

.lock-btn {
opacity: 0.5;
transition: opacity 0.2s;
&:hover {
opacity: 1;
}
}
}
}
</style>
12 changes: 12 additions & 0 deletions plugins/card-resources/src/components/icons/Lock.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<script lang="ts">
import { IconSize } from '@hcengineering/ui'

export let size: IconSize
export let fill: string = 'currentColor'
</script>

<svg class="svg-{size}" {fill} viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg">
<path
d="M4.69141 14.6338H11.3018C12.2178 14.6338 12.6689 14.1826 12.6689 13.1914V8.08496C12.6689 7.18945 12.293 6.72461 11.541 6.64941V4.96094C11.541 2.36328 9.81152 1.1123 7.99316 1.1123C6.18164 1.1123 4.45215 2.36328 4.45215 4.96094V6.67676C3.74805 6.78613 3.32422 7.2373 3.32422 8.08496V13.1914C3.32422 14.1826 3.77539 14.6338 4.69141 14.6338ZM5.75098 4.83105C5.75098 3.22461 6.76953 2.35645 7.99316 2.35645C9.2168 2.35645 10.2422 3.22461 10.2422 4.83105V6.64258L5.75098 6.64941V4.83105Z"
/>
</svg>
12 changes: 12 additions & 0 deletions plugins/card-resources/src/components/icons/Unlock.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<script lang="ts">
import { IconSize } from '@hcengineering/ui'

export let size: IconSize
export let fill: string = 'currentColor'
</script>

<svg class="svg-{size}" {fill} viewBox="0 0 16 16" xmlns="http://www.w3.org/2000/svg">
<path
d="M2.33301 14.6338H8.94336C9.85938 14.6338 10.3105 14.1826 10.3105 13.1914V8.08496C10.3105 7.2168 9.95508 6.75195 9.24414 6.65625V4.83105C9.24414 3.22461 10.2627 2.35645 11.4863 2.35645C12.71 2.35645 13.7354 3.22461 13.7354 4.83105V6.28711C13.7354 6.76562 14.0156 7.01855 14.3848 7.01855C14.7471 7.01855 15.0273 6.7793 15.0273 6.28711V4.96094C15.0273 2.36328 13.2979 1.1123 11.4863 1.1123C9.6748 1.1123 7.94531 2.36328 7.94531 4.96094V6.64258L2.44922 6.64941C1.5332 6.64941 0.96582 7.10742 0.96582 8.08496V13.1914C0.96582 14.1826 1.41699 14.6338 2.33301 14.6338Z"
/>
</svg>
Loading
Loading