Skip to content

Commit

Permalink
UBER-159: popup dialog for deleting with message if not enough permis…
Browse files Browse the repository at this point in the history
…sions (#3224)

Signed-off-by: Vyacheslav Tumanov <me@slavatumanov.me>
  • Loading branch information
ThetaDR committed May 23, 2023
1 parent 237ae70 commit 14fbe03
Show file tree
Hide file tree
Showing 7 changed files with 99 additions and 8 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
<!--
// 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 { Card, createQuery } from '@hcengineering/presentation'
import { AccountRole, Doc, getCurrentAccount, Ref, SortingOrder } from '@hcengineering/core'
import view from '@hcengineering/view-resources/src/plugin'
import { createEventDispatcher } from 'svelte'
import contact, { Employee, EmployeeAccount } from '@hcengineering/contact'
import EmployeePresenter from './EmployeePresenter.svelte'
import { employeeAccountByIdStore } from '../utils'
import ui, { Label } from '@hcengineering/ui'
export let object: Doc | Doc[]
export let deleteAction: () => void
const objectArray = Array.isArray(object) ? object : [object]
let owners: Ref<Employee>[] = []
const query = createQuery()
query.query(
contact.class.EmployeeAccount,
{ role: AccountRole.Owner },
(res) => {
owners = res.map((account) => account.employee)
},
{
sort: { name: SortingOrder.Descending }
}
)
const dispatch = createEventDispatcher()
const creators = [
...new Set(objectArray.map((obj) => $employeeAccountByIdStore.get(obj.createdBy as Ref<EmployeeAccount>)?.employee))
]
const me = $employeeAccountByIdStore.get(getCurrentAccount()._id as Ref<EmployeeAccount>)?.employee
const canDelete = (creators.length === 1 && creators.includes(me)) || (me && owners.includes(me))
const label = canDelete ? view.string.DeleteObject : view.string.DeletePopupNoPermissionTitle
</script>

<Card {label} okAction={deleteAction} canSave={canDelete} okLabel={ui.string.Ok} on:close={() => dispatch('close')}>
<div class="flex-grow flex-col">
{#if canDelete}
<div class="mb-2">
<Label label={view.string.DeleteObjectConfirm} params={{ count: objectArray.length }} />
</div>
{:else}
<div class="mb-2">
<Label label={view.string.DeletePopupNoPermissionLabel} />
</div>
<div class="mb-2">
<Label label={view.string.DeletePopupCreatorLabel} />
{#each creators as employee}
<div class="my-2">
<EmployeePresenter value={employee} />
</div>
{/each}
</div>
<div class="mb-2">
<Label label={view.string.DeletePopupOwnerLabel} />
{#each owners as employee}
<div class="my-2">
<EmployeePresenter value={employee} />
</div>
{/each}
</div>
{/if}
</div>
</Card>
4 changes: 3 additions & 1 deletion plugins/contact-resources/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ import UserBoxItems from './components/UserBoxItems.svelte'
import EmployeeFilter from './components/EmployeeFilter.svelte'
import EmployeeFilterValuePresenter from './components/EmployeeFilterValuePresenter.svelte'
import EmployeeAccountFilterValuePresenter from './components/EmployeeAccountFilterValuePresenter.svelte'
import DeleteConfirmationPopup from './components/DeleteConfirmationPopup.svelte'

import contact from './plugin'
import {
Expand Down Expand Up @@ -298,7 +299,8 @@ export default async (): Promise<Resources> => ({
UserBoxItems,
EmployeeFilter,
EmployeeFilterValuePresenter,
EmployeeAccountFilterValuePresenter
EmployeeAccountFilterValuePresenter,
DeleteConfirmationPopup
},
completion: {
EmployeeQuery: async (
Expand Down
3 changes: 2 additions & 1 deletion plugins/contact/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -194,7 +194,8 @@ export const contactPlugin = plugin(contactId, {
Avatar: '' as AnyComponent,
UserBoxList: '' as AnyComponent,
ChannelPresenter: '' as AnyComponent,
SpaceMembers: '' as AnyComponent
SpaceMembers: '' as AnyComponent,
DeleteConfirmationPopup: '' as AnyComponent
},
channelProvider: {
Email: '' as Ref<ChannelProvider>,
Expand Down
6 changes: 5 additions & 1 deletion plugins/view-assets/lang/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,11 @@
"Table": "Table",
"Role": "Role",
"DeleteObject": "Delete object",
"DeleteObjectConfirm": "Do you want to delete this {count, plural, =1 {object} other {# objects}}?",
"DeleteObjectConfirm": "Do you want to delete {count, plural, =1 {this object} other {these # objects}}?",
"DeletePopupNoPermissionTitle": "Not enough permissions to delete.",
"DeletePopupNoPermissionLabel": "Please contact people from the list below for them to do so.",
"DeletePopupCreatorLabel": "Creators (can delete only ones that were created by them):",
"DeletePopupOwnerLabel": "Owners (can delete all of them):",
"Archive": "Archive",
"ArchiveConfirm": "Do you want to archive this {count, plural, =1 {object} other {# objects}}?",
"Open": "Open",
Expand Down
4 changes: 4 additions & 0 deletions plugins/view-assets/lang/ru.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,10 @@
"Role": "Роль",
"DeleteObject": "Удалить объект",
"DeleteObjectConfirm": "Вы действительно хотите удалить {count, plural, =1 {этот объект} other {эти # объекта}}?",
"DeletePopupNoPermissionTitle": "Недостаточно прав для удаления.",
"DeletePopupNoPermissionLabel": "Пожалуйста обратитесь к людям из списка ниже, чтобы они это сделали.",
"DeletePopupCreatorLabel": "Создатели объектов (могут удалить лишь те, что были созданы ими):",
"DeletePopupOwnerLabel": "Владельцы (могут удалить все):",
"Archive": "Архивировать",
"ArchiveConfirm": "Вы действительно хотите заархивировать {count, plural, =1 {этот объект} other {эти # объекта}}?",
"Open": "Открыть",
Expand Down
9 changes: 4 additions & 5 deletions plugins/view-resources/src/actionImpl.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import { ContextStore, contextStore } from './context'
import view from './plugin'
import { FocusSelection, SelectDirection, focusStore, previewDocument, selectionStore } from './selection'
import { deleteObjects, getObjectLinkFragment } from './utils'
import contact from '@hcengineering/contact'

/**
* Action to be used for copying text to clipboard.
Expand Down Expand Up @@ -55,12 +56,10 @@ async function CopyTextToClipboard (

function Delete (object: Doc | Doc[]): void {
showPopup(
MessageBox,
contact.component.DeleteConfirmationPopup,
{
label: view.string.DeleteObject,
message: view.string.DeleteObjectConfirm,
params: { count: Array.isArray(object) ? object.length : 1 },
action: async () => {
object,
deleteAction: async () => {
const objs = Array.isArray(object) ? object : [object]
await deleteObjects(getClient(), objs).catch((err) => console.error(err))
}
Expand Down
4 changes: 4 additions & 0 deletions plugins/view-resources/src/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,10 @@ export default mergeIds(viewId, view, {
ChooseAColor: '' as IntlString,
DeleteObject: '' as IntlString,
DeleteObjectConfirm: '' as IntlString,
DeletePopupNoPermissionTitle: '' as IntlString,
DeletePopupNoPermissionLabel: '' as IntlString,
DeletePopupCreatorLabel: '' as IntlString,
DeletePopupOwnerLabel: '' as IntlString,
Archive: '' as IntlString,
ArchiveConfirm: '' as IntlString,
Assignees: '' as IntlString,
Expand Down

0 comments on commit 14fbe03

Please sign in to comment.