mirror of
https://github.com/dbeaver/cloudbeaver.git
synced 2026-09-24 16:04:36 +08:00
chore(core): some improvements
CB-142
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
{
|
||||
"authentication_administration_item": "Users",
|
||||
"authentication_administration_confirm_user_deletion": "Confirm user deletion",
|
||||
"authentication_create_user_dialog_title": "Create new user",
|
||||
"authentication_create_user_dialog_create": "Create",
|
||||
"authentication_user_name": "User name",
|
||||
|
||||
+1
-1
@@ -91,7 +91,7 @@ export const CreateUserDialog: DialogComponent<null, null> = observer(
|
||||
)}
|
||||
onReject={props.rejectDialog}
|
||||
>
|
||||
<SubmittingForm onSubmit={controller.create}>
|
||||
<SubmittingForm onSubmit={controller.create} autoComplete="disabled">
|
||||
<create-form as='div'>
|
||||
<group as="div">
|
||||
<InputField
|
||||
|
||||
+21
-5
@@ -10,7 +10,7 @@ import { observable } from 'mobx';
|
||||
|
||||
import { ErrorDetailsDialog } from '@dbeaver/core/app';
|
||||
import { injectable } from '@dbeaver/core/di';
|
||||
import { CommonDialogService } from '@dbeaver/core/dialogs';
|
||||
import { CommonDialogService, ConfirmationDialog } from '@dbeaver/core/dialogs';
|
||||
import { NotificationService } from '@dbeaver/core/eventsLog';
|
||||
import { GQLErrorCatcher } from '@dbeaver/core/sdk';
|
||||
|
||||
@@ -56,11 +56,27 @@ export class UsersAdministrationController {
|
||||
}
|
||||
|
||||
this.isDeleting = true;
|
||||
|
||||
try {
|
||||
for (const [userId, selected] of this.selectedItems) {
|
||||
if (selected) {
|
||||
await this.usersManagerService.delete(userId);
|
||||
}
|
||||
const deletionList = Array
|
||||
.from(this.selectedItems)
|
||||
.filter(([_, value]) => value)
|
||||
.map(([userId]) => userId);
|
||||
if (deletionList.length === 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
const confirmed = await this.commonDialogService.open(ConfirmationDialog, {
|
||||
title: 'authentication_administration_confirm_user_deletion',
|
||||
message: `Would you like to delete users: ${deletionList.join(', ')}`,
|
||||
});
|
||||
|
||||
if (!confirmed) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (const userId of deletionList) {
|
||||
await this.usersManagerService.delete(userId);
|
||||
}
|
||||
this.selectedItems.clear();
|
||||
await this.usersManagerService.users.refresh(undefined);
|
||||
|
||||
@@ -33,6 +33,7 @@
|
||||
"ui_processing_cancel": "Cancel",
|
||||
"ui_processing_canceling": "Canceling...",
|
||||
"ui_processing_retry": "Retry",
|
||||
"ui_processing_ok": "Ok",
|
||||
"ui_error_message": "Error:",
|
||||
"ui_errors_details": "Details",
|
||||
"ui_search": "Search...",
|
||||
|
||||
@@ -33,6 +33,7 @@
|
||||
"ui_processing_cancel": "Отменить",
|
||||
"ui_processing_canceling": "Отмена...",
|
||||
"ui_processing_retry": "Повторить",
|
||||
"ui_processing_ok": "Принять",
|
||||
"ui_error_message": "Ошибка:",
|
||||
"ui_errors_details": "Информация",
|
||||
"ui_search": "Поиск...",
|
||||
|
||||
@@ -22,7 +22,7 @@ const styles = css`
|
||||
padding: 12px 0;
|
||||
|
||||
& label {
|
||||
width: 230px;
|
||||
width: 150px;
|
||||
text-align: right;
|
||||
padding: 0 12px;
|
||||
line-height: 16px;
|
||||
|
||||
@@ -28,7 +28,7 @@ export const PROPERTIES_TABLE_STYLES = composes(
|
||||
properties-header {
|
||||
box-sizing: border-box;
|
||||
display: inline-flex;
|
||||
padding: 5px 1px;
|
||||
padding: 2px;
|
||||
position: sticky;
|
||||
z-index: 1;
|
||||
top: 0;
|
||||
|
||||
@@ -7,11 +7,12 @@
|
||||
*/
|
||||
|
||||
import { observer } from 'mobx-react';
|
||||
import { useContext } from 'react';
|
||||
import { useContext, useCallback } from 'react';
|
||||
import styled from 'reshadow';
|
||||
|
||||
import { useStyles } from '@dbeaver/core/theming';
|
||||
|
||||
import { TableContext } from './TableContext';
|
||||
import { TableItemContext } from './TableItemContext';
|
||||
|
||||
type Props = {
|
||||
@@ -19,12 +20,17 @@ type Props = {
|
||||
}
|
||||
|
||||
export const TableItemSelect = observer(function TableItemSelect({ className }: Props) {
|
||||
const tableContext = useContext(TableContext);
|
||||
const context = useContext(TableItemContext);
|
||||
if (!context) {
|
||||
return null;
|
||||
}
|
||||
const handleClick = useCallback((event: React.MouseEvent<HTMLInputElement, MouseEvent>) => {
|
||||
event.stopPropagation();
|
||||
tableContext?.setItemSelect(context.item, !context.isSelected());
|
||||
}, [tableContext, context]);
|
||||
|
||||
return styled(useStyles())(
|
||||
<input type='checkbox' checked={context.isSelected()} className={className}/>
|
||||
<input type='checkbox' checked={context.isSelected()} onClick={handleClick} className={className}/>
|
||||
);
|
||||
});
|
||||
|
||||
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
* cloudbeaver - Cloud Database Manager
|
||||
* Copyright (C) 2020 DBeaver Corp and others
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0.
|
||||
* you may not use this file except in compliance with the License.
|
||||
*/
|
||||
|
||||
import styled, { use } from 'reshadow';
|
||||
|
||||
import { Icon } from '@dbeaver/core/blocks';
|
||||
import { useStyles } from '@dbeaver/core/theming';
|
||||
|
||||
import { commonDialogStyle } from './styles';
|
||||
|
||||
export type CommonDialogWrapperProps = {
|
||||
title: string;
|
||||
onReject?: () => void;
|
||||
className?: string;
|
||||
noBodyPadding?: boolean;
|
||||
footer?: JSX.Element | boolean;
|
||||
header?: JSX.Element | boolean;
|
||||
children?: React.ReactNode;
|
||||
}
|
||||
|
||||
export function CommonDialogWrapper({
|
||||
title,
|
||||
header,
|
||||
footer,
|
||||
noBodyPadding,
|
||||
className,
|
||||
onReject,
|
||||
children,
|
||||
}: CommonDialogWrapperProps) {
|
||||
|
||||
return styled(useStyles(commonDialogStyle))(
|
||||
<dialog className={className}>
|
||||
<header>
|
||||
<header-title as="div">
|
||||
<h1>{title}</h1>
|
||||
{onReject && (
|
||||
<reject as="div">
|
||||
<Icon name="cross" viewBox="0 0 16 16" onClick={onReject} />
|
||||
</reject>
|
||||
)}
|
||||
</header-title>
|
||||
{header}
|
||||
</header>
|
||||
<dialog-body as="div" {...use({ noPadding: noBodyPadding })}>{children}</dialog-body>
|
||||
<footer>
|
||||
{footer}
|
||||
</footer>
|
||||
</dialog>
|
||||
);
|
||||
}
|
||||
+3
-44
@@ -6,22 +6,12 @@
|
||||
* you may not use this file except in compliance with the License.
|
||||
*/
|
||||
|
||||
import styled, { css, use } from 'reshadow';
|
||||
|
||||
import { Icon } from '@dbeaver/core/blocks';
|
||||
import { composes, useStyles } from '@dbeaver/core/theming';
|
||||
import { css } from 'reshadow';
|
||||
|
||||
export type CommonDialogWrapperProps = {
|
||||
title: string;
|
||||
onReject?: () => void;
|
||||
className?: string;
|
||||
noBodyPadding?: boolean;
|
||||
footer?: JSX.Element | boolean;
|
||||
header?: JSX.Element | boolean;
|
||||
children?: React.ReactNode;
|
||||
}
|
||||
import { composes } from '@dbeaver/core/theming';
|
||||
|
||||
const style = composes(
|
||||
export const commonDialogStyle = composes(
|
||||
css`
|
||||
dialog {
|
||||
composes: theme-background-surface theme-text-on-surface from global;
|
||||
@@ -91,34 +81,3 @@ const style = composes(
|
||||
}
|
||||
`
|
||||
);
|
||||
|
||||
export function CommonDialogWrapper({
|
||||
title,
|
||||
header,
|
||||
footer,
|
||||
noBodyPadding,
|
||||
className,
|
||||
onReject,
|
||||
children,
|
||||
}: CommonDialogWrapperProps) {
|
||||
|
||||
return styled(useStyles(style))(
|
||||
<dialog className={className}>
|
||||
<header>
|
||||
<header-title as="div">
|
||||
<h1>{title}</h1>
|
||||
{onReject && (
|
||||
<reject as="div">
|
||||
<Icon name="cross" viewBox="0 0 16 16" onClick={onReject} />
|
||||
</reject>
|
||||
)}
|
||||
</header-title>
|
||||
{header}
|
||||
</header>
|
||||
<dialog-body as="div" {...use({ noPadding: noBodyPadding })}>{children}</dialog-body>
|
||||
<footer>
|
||||
{footer}
|
||||
</footer>
|
||||
</dialog>
|
||||
);
|
||||
}
|
||||
@@ -19,6 +19,7 @@ export type DialogComponentProps<TPayload, TResult> = {
|
||||
options?: DialogOptions;
|
||||
resolveDialog(result: TResult | null): void;
|
||||
rejectDialog(): void; // the dialog was closed by cancel button or backdrop click
|
||||
className?: string;
|
||||
}
|
||||
|
||||
export type DialogComponent<TPayload, TResult> = React.ElementType<
|
||||
|
||||
@@ -0,0 +1,74 @@
|
||||
/*
|
||||
* cloudbeaver - Cloud Database Manager
|
||||
* Copyright (C) 2020 DBeaver Corp and others
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0.
|
||||
* you may not use this file except in compliance with the License.
|
||||
*/
|
||||
|
||||
import { useCallback } from 'react';
|
||||
import styled, { css } from 'reshadow';
|
||||
|
||||
import { Icon, Button } from '@dbeaver/core/blocks';
|
||||
import { Translate } from '@dbeaver/core/localization';
|
||||
import { useStyles } from '@dbeaver/core/theming';
|
||||
|
||||
import { commonDialogStyle } from './CommonDialog/styles';
|
||||
import { DialogComponentProps } from './CommonDialogService';
|
||||
|
||||
const style = css`
|
||||
footer {
|
||||
align-items: center;
|
||||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
fill {
|
||||
flex: 1;
|
||||
}
|
||||
`;
|
||||
|
||||
export interface ConfirmationDialogPayload {
|
||||
title: string;
|
||||
message: string;
|
||||
}
|
||||
|
||||
export function ConfirmationDialog({
|
||||
payload,
|
||||
resolveDialog,
|
||||
rejectDialog,
|
||||
className,
|
||||
}: DialogComponentProps<ConfirmationDialogPayload, boolean>) {
|
||||
const handleReject = useCallback(() => resolveDialog(false), [resolveDialog]);
|
||||
const handleResolve = useCallback(() => resolveDialog(true), [resolveDialog]);
|
||||
|
||||
return styled(useStyles(commonDialogStyle, style))(
|
||||
<dialog className={className}>
|
||||
<header>
|
||||
<header-title as="div">
|
||||
<h1><Translate token={payload.title}/></h1>
|
||||
<reject as="div">
|
||||
<Icon name="cross" viewBox="0 0 16 16" onClick={handleReject} />
|
||||
</reject>
|
||||
</header-title>
|
||||
</header>
|
||||
<dialog-body as="div"><Translate token={payload.message}/></dialog-body>
|
||||
<footer>
|
||||
<Button
|
||||
type="button"
|
||||
mod={['outlined']}
|
||||
onClick={handleReject}
|
||||
>
|
||||
<Translate token='ui_processing_cancel'/>
|
||||
</Button>
|
||||
<fill as="div"/>
|
||||
<Button
|
||||
type="button"
|
||||
mod={['unelevated']}
|
||||
onClick={handleResolve}
|
||||
>
|
||||
<Translate token='ui_processing_ok'/>
|
||||
</Button>
|
||||
</footer>
|
||||
</dialog>
|
||||
);
|
||||
}
|
||||
@@ -14,8 +14,8 @@ import { Button } from '@dbeaver/core/blocks';
|
||||
import { useTranslate } from '@dbeaver/core/localization';
|
||||
import { useStyles } from '@dbeaver/core/theming';
|
||||
|
||||
import { CommonDialogWrapper } from '../CommonDialog/CommonDialog/CommonDialogWrapper';
|
||||
import { DialogComponent } from '../CommonDialog/CommonDialogService';
|
||||
import { CommonDialogWrapper } from '../CommonDialog/CommonDialogWrapper';
|
||||
|
||||
const styles = css`
|
||||
dialog-content {
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
export * from './CommonDialog/CommonDialog/CommonDialogWrapper';
|
||||
export * from './CommonDialog/CommonDialogService';
|
||||
export * from './CommonDialog/CommonDialogWrapper';
|
||||
export * from './CommonDialog/ConfirmationDialog';
|
||||
export * from './CommonDialog/DialogsPortal';
|
||||
|
||||
export * from './Menu/IMenuPanel';
|
||||
|
||||
Reference in New Issue
Block a user