mirror of
https://github.com/dbeaver/cloudbeaver.git
synced 2026-09-24 16:04:36 +08:00
Merge pull request #144 from dbeaver/feat-access-managment
chore: improve administration page styles
This commit is contained in:
-1
@@ -30,7 +30,6 @@ const styles = composes(
|
||||
css`
|
||||
layout-grid {
|
||||
width: 100%;
|
||||
max-width: 1176px;
|
||||
}
|
||||
|
||||
layout-grid-cell {
|
||||
|
||||
+8
@@ -72,6 +72,10 @@ const styles = composes(
|
||||
outline: none;
|
||||
}
|
||||
|
||||
TabPanel {
|
||||
overflow: auto !important;
|
||||
}
|
||||
|
||||
Tab {
|
||||
composes: theme-typography--body2 from global;
|
||||
text-transform: uppercase;
|
||||
@@ -80,6 +84,10 @@ const styles = composes(
|
||||
&:global([aria-selected=true]) {
|
||||
font-weight: normal !important;
|
||||
}
|
||||
|
||||
& TabTitle {
|
||||
padding: 0 24px !important;
|
||||
}
|
||||
}
|
||||
|
||||
ErrorMessage {
|
||||
|
||||
+2
-1
@@ -50,7 +50,8 @@ implements IInitializableController, IDestructibleController {
|
||||
};
|
||||
|
||||
@computed get users() {
|
||||
return Array.from(this.usersResource.data.values());
|
||||
return Array.from(this.usersResource.data.values())
|
||||
.filter(user => !this.usersResource.isNew(user.userId));
|
||||
}
|
||||
|
||||
@computed get roles() {
|
||||
|
||||
+111
-102
@@ -7,7 +7,7 @@
|
||||
*/
|
||||
|
||||
import { observer } from 'mobx-react';
|
||||
import styled, { use } from 'reshadow';
|
||||
import styled, { css } from 'reshadow';
|
||||
|
||||
import {
|
||||
Radio, InputField, useFocus, ObjectPropertyInfoForm, Combobox, Checkbox, Textarea, InputGroup
|
||||
@@ -24,124 +24,133 @@ type ConnectionFormProps = {
|
||||
controller: IFormController;
|
||||
}
|
||||
|
||||
const styles = css`
|
||||
box {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
box-element {
|
||||
min-width: 450px;
|
||||
}
|
||||
`;
|
||||
|
||||
export const ConnectionForm = observer(function ConnectionForm({
|
||||
controller,
|
||||
}: ConnectionFormProps) {
|
||||
const translate = useTranslate();
|
||||
const [focusedRef] = useFocus({ focusFirstChild: true });
|
||||
|
||||
return styled(useStyles(formStyles))(
|
||||
return styled(useStyles(styles, formStyles))(
|
||||
<connection-form as='div' ref={focusedRef as React.RefObject<HTMLDivElement>}>
|
||||
<layout-grid as="div">
|
||||
<layout-grid-inner as="div">
|
||||
<layout-grid-cell as='div' {...use({ 'span-tablet': 12, 'span-desktop': 5 })}>
|
||||
<group as="div">
|
||||
<Checkbox
|
||||
name="template"
|
||||
value={controller.connectionId}
|
||||
checkboxLabel={translate('connections_connection_template')}
|
||||
checked={controller.config.template}
|
||||
onChange={value => controller.onChange('template', value)}
|
||||
disabled={!controller.isNew || controller.isDisabled}
|
||||
mod='surface'
|
||||
/>
|
||||
</group>
|
||||
<group as="div">
|
||||
<Combobox
|
||||
value={controller.driver?.id}
|
||||
items={controller.drivers}
|
||||
keySelector={driver => driver.id}
|
||||
valueSelector={driver => driver?.name!}
|
||||
onSelect={controller.onSelectDriver}
|
||||
readOnly={!controller.isNew}
|
||||
mod={'surface'}
|
||||
>
|
||||
{translate('connections_connection_driver')}
|
||||
</Combobox>
|
||||
</group>
|
||||
<box as="div">
|
||||
<box-element as='div'>
|
||||
<group as="div">
|
||||
<Checkbox
|
||||
name="template"
|
||||
value={controller.connectionId}
|
||||
checkboxLabel={translate('connections_connection_template')}
|
||||
checked={controller.config.template}
|
||||
onChange={value => controller.onChange('template', value)}
|
||||
disabled={!controller.isNew || controller.isDisabled}
|
||||
mod='surface'
|
||||
/>
|
||||
</group>
|
||||
<group as="div">
|
||||
<Combobox
|
||||
value={controller.driver?.id}
|
||||
items={controller.drivers}
|
||||
keySelector={driver => driver.id}
|
||||
valueSelector={driver => driver?.name!}
|
||||
onSelect={controller.onSelectDriver}
|
||||
readOnly={!controller.isNew}
|
||||
mod={'surface'}
|
||||
>
|
||||
{translate('connections_connection_driver')}
|
||||
</Combobox>
|
||||
</group>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type="text"
|
||||
name="name"
|
||||
value={controller.config.name}
|
||||
onChange={value => controller.onChange('name', value)}
|
||||
disabled={controller.isDisabled}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('connections_connection_name')}
|
||||
</InputField>
|
||||
</group>
|
||||
<group as="div">
|
||||
<Textarea
|
||||
name="description"
|
||||
rows={3}
|
||||
value={controller.config.description}
|
||||
onChange={value => controller.onChange('description', value)}
|
||||
disabled={controller.isDisabled}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('connections_connection_description')}
|
||||
</Textarea>
|
||||
</group>
|
||||
</box-element>
|
||||
<box-element as='div'>
|
||||
<connection-type as="div">
|
||||
<Radio
|
||||
name="type"
|
||||
id={`${controller.connectionId}custom`}
|
||||
value={'custom'}
|
||||
onClick={() => controller.onChangeType(ConnectionType.Attributes)}
|
||||
checked={controller.connectionType === ConnectionType.Attributes}
|
||||
disabled={controller.isDisabled}
|
||||
mod={['primary']}
|
||||
>
|
||||
{translate('customConnection_connectionType_custom')}
|
||||
</Radio>
|
||||
<Radio
|
||||
name="type"
|
||||
id={`${controller.connectionId}url`}
|
||||
value={'url'}
|
||||
onClick={() => controller.onChangeType(ConnectionType.URL)}
|
||||
checked={controller.connectionType === ConnectionType.URL}
|
||||
disabled={controller.isDisabled}
|
||||
mod={['primary']}
|
||||
>
|
||||
{translate('customConnection_connectionType_url')}
|
||||
</Radio>
|
||||
</connection-type>
|
||||
{controller.connectionType === ConnectionType.Attributes ? (
|
||||
<ParametersForm controller={controller} embedded={controller.driver?.embedded} />
|
||||
) : (
|
||||
<group as="div">
|
||||
<InputField
|
||||
type="text"
|
||||
name="name"
|
||||
value={controller.config.name}
|
||||
onChange={value => controller.onChange('name', value)}
|
||||
name="url"
|
||||
value={controller.config.url}
|
||||
onChange={value => controller.onChange('url', value)}
|
||||
disabled={controller.isDisabled}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('connections_connection_name')}
|
||||
{translate('customConnection_url_JDBC')}
|
||||
</InputField>
|
||||
</group>
|
||||
<group as="div">
|
||||
<Textarea
|
||||
name="description"
|
||||
rows={3}
|
||||
value={controller.config.description}
|
||||
onChange={value => controller.onChange('description', value)}
|
||||
disabled={controller.isDisabled}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('connections_connection_description')}
|
||||
</Textarea>
|
||||
</group>
|
||||
</layout-grid-cell>
|
||||
<layout-grid-cell as='div' {...use({ 'span-tablet': '12', 'span-desktop': 7 })}>
|
||||
<connection-type as="div">
|
||||
<Radio
|
||||
name="type"
|
||||
id={`${controller.connectionId}custom`}
|
||||
value={'custom'}
|
||||
onClick={() => controller.onChangeType(ConnectionType.Attributes)}
|
||||
checked={controller.connectionType === ConnectionType.Attributes}
|
||||
disabled={controller.isDisabled}
|
||||
mod={['primary']}
|
||||
>
|
||||
{translate('customConnection_connectionType_custom')}
|
||||
</Radio>
|
||||
<Radio
|
||||
name="type"
|
||||
id={`${controller.connectionId}url`}
|
||||
value={'url'}
|
||||
onClick={() => controller.onChangeType(ConnectionType.URL)}
|
||||
checked={controller.connectionType === ConnectionType.URL}
|
||||
disabled={controller.isDisabled}
|
||||
mod={['primary']}
|
||||
>
|
||||
{translate('customConnection_connectionType_url')}
|
||||
</Radio>
|
||||
</connection-type>
|
||||
{controller.connectionType === ConnectionType.Attributes ? (
|
||||
<ParametersForm controller={controller} embedded={controller.driver?.embedded} />
|
||||
) : (
|
||||
)}
|
||||
{controller.authModel && (
|
||||
<>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type="text"
|
||||
name="url"
|
||||
value={controller.config.url}
|
||||
onChange={value => controller.onChange('url', value)}
|
||||
disabled={controller.isDisabled}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('customConnection_url_JDBC')}
|
||||
</InputField>
|
||||
<InputGroup>{translate('connections_connection_edit_authentication')}</InputGroup>
|
||||
</group>
|
||||
)}
|
||||
{controller.authModel && (
|
||||
<>
|
||||
<group as="div">
|
||||
<InputGroup>{translate('connections_connection_edit_authentication')}</InputGroup>
|
||||
</group>
|
||||
<ObjectPropertyInfoForm
|
||||
prefix={`auth_${controller.driver?.id || ''}`}
|
||||
autofillToken={`section-${controller.driver?.id || ''} section-auth`}
|
||||
properties={controller.authModel.properties}
|
||||
credentials={controller.config.credentials}
|
||||
processing={controller.isDisabled}
|
||||
/>
|
||||
</>
|
||||
)}
|
||||
</layout-grid-cell>
|
||||
</layout-grid-inner>
|
||||
</layout-grid>
|
||||
<ObjectPropertyInfoForm
|
||||
prefix={`auth_${controller.driver?.id || ''}`}
|
||||
autofillToken={`section-${controller.driver?.id || ''} section-auth`}
|
||||
properties={controller.authModel.properties}
|
||||
credentials={controller.config.credentials}
|
||||
processing={controller.isDisabled}
|
||||
/>
|
||||
</>
|
||||
)}
|
||||
</box-element>
|
||||
</box>
|
||||
</connection-form>
|
||||
);
|
||||
});
|
||||
|
||||
@@ -84,7 +84,9 @@ layout-grid-cell {
|
||||
}
|
||||
}
|
||||
|
||||
.layout-grid--fixed-column-width {
|
||||
.layout-grid--fixed-column-width,
|
||||
layout-grid[use|fixed-width],
|
||||
.layout-grid[use|fixed-width] {
|
||||
@each $size in map-keys($mdc-layout-grid-columns) {
|
||||
@include mdc-layout-grid-media-query_($size) {
|
||||
$margin: map-get($mdc-layout-grid-default-margin, $size);
|
||||
|
||||
@@ -30,7 +30,6 @@ const styles = composes(
|
||||
css`
|
||||
layout-grid {
|
||||
width: 100%;
|
||||
max-width: 1176px;
|
||||
}
|
||||
|
||||
layout-grid-cell {
|
||||
|
||||
+76
-60
@@ -74,6 +74,10 @@ const styles = composes(
|
||||
outline: none;
|
||||
}
|
||||
|
||||
TabPanel {
|
||||
overflow: auto !important;
|
||||
}
|
||||
|
||||
Tab {
|
||||
composes: theme-typography--body2 from global;
|
||||
text-transform: uppercase;
|
||||
@@ -82,6 +86,10 @@ const styles = composes(
|
||||
&:global([aria-selected=true]) {
|
||||
font-weight: normal !important;
|
||||
}
|
||||
|
||||
& TabTitle {
|
||||
padding: 0 24px !important;
|
||||
}
|
||||
}
|
||||
|
||||
ErrorMessage {
|
||||
@@ -107,6 +115,16 @@ const styles = composes(
|
||||
flex: 1;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
flex-box {
|
||||
flex: 1;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
|
||||
flex-box-element {
|
||||
min-width: 450px;
|
||||
}
|
||||
`
|
||||
);
|
||||
|
||||
@@ -183,69 +201,67 @@ export const UserEdit = observer(function UserEdit({
|
||||
: (
|
||||
<SubmittingForm onSubmit={controller.save} ref={focusedRef as React.RefObject<HTMLFormElement>}>
|
||||
<TabPanel tabId='info'>
|
||||
<layout-grid as="div">
|
||||
<layout-grid-inner as="div">
|
||||
<layout-grid-cell as='div' {...use({ 'span-tablet': 12, 'span-desktop': 5 })}>
|
||||
<group as="div">
|
||||
<InputGroup>{translate('authentication_user_credentials')}</InputGroup>
|
||||
</group>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type='text'
|
||||
name='login'
|
||||
value={controller.credentials.login}
|
||||
onChange={handleLoginChange}
|
||||
disabled={!controller.isNew || controller.isSaving}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('authentication_user_name')}
|
||||
</InputField>
|
||||
</group>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type='password'
|
||||
name='password'
|
||||
value={controller.credentials.password}
|
||||
onChange={handlePasswordChange}
|
||||
<flex-box as="div">
|
||||
<flex-box-element as='div'>
|
||||
<group as="div">
|
||||
<InputGroup>{translate('authentication_user_credentials')}</InputGroup>
|
||||
</group>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type='text'
|
||||
name='login'
|
||||
value={controller.credentials.login}
|
||||
onChange={handleLoginChange}
|
||||
disabled={!controller.isNew || controller.isSaving}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('authentication_user_name')}
|
||||
</InputField>
|
||||
</group>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type='password'
|
||||
name='password'
|
||||
value={controller.credentials.password}
|
||||
onChange={handlePasswordChange}
|
||||
disabled={controller.isSaving}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('authentication_user_password')}
|
||||
</InputField>
|
||||
</group>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type='password'
|
||||
name='password_repeat'
|
||||
value={controller.credentials.passwordRepeat}
|
||||
onChange={handlePasswordRepeatChange}
|
||||
disabled={controller.isSaving}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('authentication_user_password_repeat')}
|
||||
</InputField>
|
||||
</group>
|
||||
</flex-box-element>
|
||||
<flex-box-element as='div'>
|
||||
<group as="div">
|
||||
<InputGroup>{translate('authentication_user_role')}</InputGroup>
|
||||
</group>
|
||||
{controller.roles.map((role, i) => (
|
||||
<group as="div" key={role.roleId}>
|
||||
<Checkbox
|
||||
value={role.roleId}
|
||||
name='role'
|
||||
checkboxLabel={role.roleName || role.roleId}
|
||||
onChange={checked => handleRoleChange(role.roleId, checked)}
|
||||
checked={controller.credentials.roles.get(role.roleId)}
|
||||
disabled={controller.isSaving}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('authentication_user_password')}
|
||||
</InputField>
|
||||
/>
|
||||
</group>
|
||||
<group as="div">
|
||||
<InputField
|
||||
type='password'
|
||||
name='password_repeat'
|
||||
value={controller.credentials.passwordRepeat}
|
||||
onChange={handlePasswordRepeatChange}
|
||||
disabled={controller.isSaving}
|
||||
mod='surface'
|
||||
>
|
||||
{translate('authentication_user_password_repeat')}
|
||||
</InputField>
|
||||
</group>
|
||||
</layout-grid-cell>
|
||||
<layout-grid-cell as='div' {...use({ 'span-tablet': 12, 'span-desktop': 5 })}>
|
||||
<group as="div">
|
||||
<InputGroup>{translate('authentication_user_role')}</InputGroup>
|
||||
</group>
|
||||
{controller.roles.map((role, i) => (
|
||||
<group as="div" key={role.roleId}>
|
||||
<Checkbox
|
||||
value={role.roleId}
|
||||
name='role'
|
||||
checkboxLabel={role.roleName || role.roleId}
|
||||
onChange={checked => handleRoleChange(role.roleId, checked)}
|
||||
checked={controller.credentials.roles.get(role.roleId)}
|
||||
disabled={controller.isSaving}
|
||||
mod='surface'
|
||||
/>
|
||||
</group>
|
||||
))}
|
||||
</layout-grid-cell>
|
||||
</layout-grid-inner>
|
||||
</layout-grid>
|
||||
))}
|
||||
</flex-box-element>
|
||||
</flex-box>
|
||||
</TabPanel>
|
||||
<TabPanel tabId='connections_access'>
|
||||
<GrantedConnections
|
||||
|
||||
+2
-1
@@ -36,7 +36,8 @@ export class UserEditController implements IInitializableController, IDestructib
|
||||
}
|
||||
|
||||
@computed get connections() {
|
||||
return Array.from(this.connectionsResource.data.values());
|
||||
return Array.from(this.connectionsResource.data.values())
|
||||
.filter(connection => !this.connectionsResource.isNew(connection.id));
|
||||
}
|
||||
|
||||
@computed get roles() {
|
||||
|
||||
Reference in New Issue
Block a user