Merge remote-tracking branch 'origin/devel' into devel

This commit is contained in:
serge-rider
2020-10-25 22:39:20 +03:00
62 changed files with 460 additions and 715 deletions
@@ -73,6 +73,7 @@ export const ElementsTree: React.FC<Props> = observer(function ElementsTree({
{nodeChildren.children.map(id => (
<NavigationNodeElement key={id} nodeId={id} />
))}
<Loader loading={nodeChildren.isLoading()} overlay />
</tree>
</TreeContext.Provider>
);
@@ -31,6 +31,7 @@ const navigationTreeStyles = css`
ElementsTree {
padding-top: 16px;
min-width: 100%;
min-height: 100%;
width: max-content;
}
@@ -8,12 +8,10 @@
import { useContext, useEffect, useState } from 'react';
import { useConnectionInfo } from '@cloudbeaver/core-connections';
import { useService } from '@cloudbeaver/core-di';
import { NavNode } from '../../shared/NodesManager/EntityTypes';
import { EObjectFeature } from '../../shared/NodesManager/EObjectFeature';
import { NodeManagerUtils } from '../../shared/NodesManager/NodeManagerUtils';
import { useNode } from '../../shared/NodesManager/useNode';
import { useChildren } from '../../shared/useChildren';
import { NavigationTreeService } from '../NavigationTreeService';
@@ -38,15 +36,19 @@ export function useNavigationNode(node: NavNode): INavigationNode {
const [processing, setProcessing] = useState(false);
const [isExpanded, switchExpand] = useState(false);
const { isLoading, isOutdated } = useNode(node.id);
const connectionId = NodeManagerUtils.connectionNodeIdToConnectionId(node.id);
const { connectionInfo } = useConnectionInfo(connectionId);
const children = useChildren(node.id);
const loading = isLoading() || children.isLoading() || processing;
let leaf = isLeaf(node) || (children.children?.length === 0 && !children.isOutdated());
let expanded = isExpanded && !leaf;
if (node.objectFeatures.includes(EObjectFeature.dataSource) && !connectionInfo?.connected) {
if (
node.objectFeatures.includes(EObjectFeature.dataSource)
&& (
!node.objectFeatures.includes(EObjectFeature.dataSourceConnected)
|| (!children.children && isOutdated())
)
) {
leaf = false;
expanded = false;
}
@@ -8,13 +8,12 @@
import { injectable } from '@cloudbeaver/core-di';
import {
GraphQLService, CachedMapResource, ResourceKey, isResourceKeyList, NavigatorNodeInfo, DatabaseObjectInfo
GraphQLService, CachedMapResource, ResourceKey, isResourceKeyList, NavNodeInfoFragment
} from '@cloudbeaver/core-sdk';
import { NavNode } from './EntityTypes';
type NavNodeInfo = Pick<NavigatorNodeInfo, 'id' | 'name' | 'hasChildren' | 'nodeType' | 'icon' | 'folder' | 'inline' | 'navigable' | 'features'>
& { object?: Pick<DatabaseObjectInfo, 'features'> };
type NavNodeInfo = NavNodeInfoFragment;
export const ROOT_NODE_PATH = '';
@@ -11,7 +11,7 @@ import {
} from '@cloudbeaver/core-connections';
import { injectable, Bootstrap } from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { IExecutor, Executor, IContextProvider } from '@cloudbeaver/core-executor';
import { IExecutor, Executor, IExecutionContextProvider } from '@cloudbeaver/core-executor';
import {
PermissionsService, EPermission, SessionResource, ServerService
} from '@cloudbeaver/core-root';
@@ -119,7 +119,7 @@ export class NavNodeManagerService extends Bootstrap {
register(): void {
this.connectionInfo.onItemAdd.subscribe(this.connectionUpdateHandler.bind(this));
this.connectionInfo.onItemDelete.subscribe(this.connectionRemoveHandler.bind(this));
this.connectionInfo.onConnectionCreate.subscribe(this.connectionCreateHandler.bind(this));
this.connectionInfo.onConnectionCreate.addHandler(this.connectionCreateHandler.bind(this));
this.sessionResource.onDataUpdate.subscribe(this.refreshRoot.bind(this));
}
@@ -253,7 +253,7 @@ export class NavNodeManagerService extends Bootstrap {
}
navigationNavNodeContext = async (
contexts: IContextProvider<INodeNavigationData>,
contexts: IExecutionContextProvider<INodeNavigationData>,
data: INodeNavigationData
): Promise<INodeNavigationContext> => {
let nodeId = data.nodeId;
@@ -332,7 +332,7 @@ export class NavNodeManagerService extends Bootstrap {
}
}
private async connectionCreateHandler(connection: Connection) {
private async connectionCreateHandler(context: IExecutionContextProvider<Connection>, connection: Connection) {
if (!await this.isNavTreeEnabled()) {
return;
}
@@ -340,7 +340,11 @@ export class NavNodeManagerService extends Bootstrap {
const nodeId = NodeManagerUtils.connectionIdToConnectionNodeId(connection.id);
this.markTreeOutdated(nodeId);
await this.navTree.refresh(ROOT_NODE_PATH);
const tree = await this.navTree.load(ROOT_NODE_PATH);
if (!tree.includes(nodeId)) {
await this.navTree.refresh(ROOT_NODE_PATH);
}
}
private async connectionUpdateHandler(key: ResourceKey<string>) {
@@ -382,7 +386,7 @@ export class NavNodeManagerService extends Bootstrap {
}
private async navigateHandler(
contexts: IContextProvider<INodeNavigationData>,
contexts: IExecutionContextProvider<INodeNavigationData>,
data: INodeNavigationData
// eslint-disable-next-line @typescript-eslint/no-invalid-void-type
): Promise<void | false> {
@@ -6,6 +6,8 @@
* you may not use this file except in compliance with the License.
*/
import { useCallback } from 'react';
import { useService } from '@cloudbeaver/core-di';
import { NavNodeInfoResource } from './NavNodeInfoResource';
@@ -13,9 +15,12 @@ import { NavNodeInfoResource } from './NavNodeInfoResource';
export function useNode(navNodeId: string) {
const navNodeInfoResource = useService(NavNodeInfoResource);
const node = navNodeInfoResource.get(navNodeId);
const isLoading = () => navNodeInfoResource.isDataLoading(navNodeId);
const isLoaded = () => navNodeInfoResource.isLoaded(navNodeId);
const isOutdated = () => navNodeInfoResource.isOutdated(navNodeId);
const deps = [navNodeId];
const isLoading = useCallback(() => navNodeInfoResource.isDataLoading(navNodeId), deps);
const isLoaded = useCallback(() => navNodeInfoResource.isLoaded(navNodeId), deps);
const isOutdated = useCallback(() => navNodeInfoResource.isOutdated(navNodeId), deps);
return {
node, isLoading, isLoaded, isOutdated,
@@ -6,6 +6,8 @@
* you may not use this file except in compliance with the License.
*/
import { useCallback } from 'react';
import { useService } from '@cloudbeaver/core-di';
import { ROOT_NODE_PATH } from './NodesManager/NavNodeInfoResource';
@@ -21,9 +23,12 @@ interface Hook {
export function useChildren(navNodeId = ROOT_NODE_PATH): Hook {
const navTreeResource = useService(NavTreeResource);
const children = navTreeResource.get(navNodeId);
const isLoading = () => navTreeResource.isDataLoading(navNodeId);
const isLoaded = () => navTreeResource.isLoaded(navNodeId);
const isOutdated = () => navTreeResource.isOutdated(navNodeId);
const deps = [navNodeId];
const isLoading = useCallback(() => navTreeResource.isDataLoading(navNodeId), deps);
const isLoaded = useCallback(() => navTreeResource.isLoaded(navNodeId), deps);
const isOutdated = useCallback(() => navTreeResource.isOutdated(navNodeId), deps);
return {
children,
@@ -6,8 +6,7 @@
* you may not use this file except in compliance with the License.
*/
import { observer } from 'mobx-react';
import { useMemo, useRef } from 'react';
import { useCallback, useMemo, useRef, memo } from 'react';
import styled, { use } from 'reshadow';
import { useStyles } from '@cloudbeaver/core-theming';
@@ -26,7 +25,7 @@ interface Props {
onOpen?: () => void;
}
export const TreeNode: React.FC<Props> = observer(function TreeNode({
export const TreeNode: React.FC<Props> = memo(function TreeNode({
loading = false,
selected = false,
expanded = false,
@@ -38,15 +37,18 @@ export const TreeNode: React.FC<Props> = observer(function TreeNode({
const handlersRef = useRef(handlers);
handlersRef.current = handlers;
const handleExpand = () => {
const handleExpand = useCallback(() => {
handlersRef.current.onExpand?.();
};
}, []);
const handleSelect = (multiple?: boolean): boolean => handlersRef.current.onSelect?.(multiple) || false;
const handleSelect = useCallback(
(multiple?: boolean): boolean => handlersRef.current.onSelect?.(multiple) || false,
[]
);
const handleOpen = () => {
const handleOpen = useCallback(() => {
handlersRef.current.onOpen?.();
};
}, []);
const nodeContext = useMemo<ITreeNodeContext>(() => ({
loading,
@@ -6,7 +6,6 @@
* you may not use this file except in compliance with the License.
*/
import { observer } from 'mobx-react';
import { useContext } from 'react';
import { TreeNodeContext } from './TreeNodeContext';
@@ -20,7 +19,7 @@ interface Props {
big?: boolean;
}
export const TreeNodeControl: React.FC<Props> = observer(function TreeNodeControl({
export const TreeNodeControl: React.FC<Props> = function TreeNodeControl({
className,
children,
}) {
@@ -57,4 +56,4 @@ export const TreeNodeControl: React.FC<Props> = observer(function TreeNodeContro
{children}
</div>
);
});
};
@@ -6,7 +6,6 @@
* you may not use this file except in compliance with the License.
*/
import { observer } from 'mobx-react';
import { useContext } from 'react';
import styled from 'reshadow';
import { css } from 'reshadow';
@@ -33,7 +32,7 @@ interface Props {
className?: string;
}
export const TreeNodeExpand: React.FC<Props> = observer(function TreeNodeExpand({
export const TreeNodeExpand: React.FC<Props> = function TreeNodeExpand({
leaf,
big,
className,
@@ -62,4 +61,4 @@ export const TreeNodeExpand: React.FC<Props> = observer(function TreeNodeExpand(
{!context.loading && !context.leaf && !leaf && !big && <Icon name="arrow" viewBox="0 0 16 16" />}
</arrow>
);
});
};
@@ -6,7 +6,6 @@
* you may not use this file except in compliance with the License.
*/
import { observer } from 'mobx-react';
import { useContext } from 'react';
import styled from 'reshadow';
import { css } from 'reshadow';
@@ -26,7 +25,7 @@ interface Props {
className?: string;
}
export const TreeNodeSelect: React.FC<Props> = observer(function TreeNodeSelect({
export const TreeNodeSelect: React.FC<Props> = function TreeNodeSelect({
className,
}) {
const context = useContext(TreeNodeContext);
@@ -49,4 +48,4 @@ export const TreeNodeSelect: React.FC<Props> = observer(function TreeNodeSelect(
<Checkbox checked={context.selected} onChange={() => context.select(true)} />
</div>
);
});
};
@@ -6,10 +6,12 @@
* you may not use this file except in compliance with the License.
*/
import { ConnectionInfo, AdminConnectionGrantInfo } from '@cloudbeaver/core-sdk';
import { AdminConnectionGrantInfo } from '@cloudbeaver/core-sdk';
import { AdminConnection } from '../../ConnectionsResource';
export interface IConnectionFormModel {
connection: ConnectionInfo;
connection: AdminConnection;
credentials: Record<string, string | number>;
grantedSubjects: AdminConnectionGrantInfo[] | null;
availableDrivers: string[];
@@ -11,11 +11,12 @@ import styled, { css, use } from 'reshadow';
import { FormGroup, InputField } from '@cloudbeaver/core-blocks';
import { useTranslate } from '@cloudbeaver/core-localization';
import { ConnectionInfo } from '@cloudbeaver/core-sdk';
import { useStyles } from '@cloudbeaver/core-theming';
import { AdminConnection } from '../../../ConnectionsResource';
interface ParametersFormProps {
connection: ConnectionInfo;
connection: AdminConnection;
disabled?: boolean;
embedded?: boolean;
}
@@ -11,9 +11,9 @@ import { observable, computed } from 'mobx';
import { injectable } from '@cloudbeaver/core-di';
import { CommonDialogService, ConfirmationDialog, DialogueStateResult } from '@cloudbeaver/core-dialogs';
import { NotificationService } from '@cloudbeaver/core-events';
import { ConnectionInfo, resourceKeyList } from '@cloudbeaver/core-sdk';
import { resourceKeyList } from '@cloudbeaver/core-sdk';
import { ConnectionsResource } from '../ConnectionsResource';
import { AdminConnection, ConnectionsResource } from '../ConnectionsResource';
import { ConnectionsAdministrationNavService } from './ConnectionsAdministrationNavService';
@injectable()
@@ -22,7 +22,7 @@ export class ConnectionsAdministrationController {
readonly selectedItems = observable<string, boolean>(new Map());
readonly expandedItems = observable<string, boolean>(new Map());
@computed
get connections(): ConnectionInfo[] {
get connections(): AdminConnection[] {
return Array.from(this.connectionsResource.data.values())
.sort((a, b) => {
const isANew = this.connectionsResource.isNew(a.id);
@@ -13,13 +13,13 @@ import { Tab, TabTitle, TabIcon } from '@cloudbeaver/core-blocks';
import { Translate } from '@cloudbeaver/core-localization';
import { useStyles } from '@cloudbeaver/core-theming';
export function ConnectionsDrawerItem({
export const ConnectionsDrawerItem: React.FC<AdministrationItemDrawerProps> = function ConnectionsDrawerItem({
item, onSelect, style, disabled, configurationWizard,
}: AdministrationItemDrawerProps) {
}) {
return styled(useStyles(...style))(
<Tab tabId={item.name} disabled={disabled} onOpen={() => onSelect(item.name)}>
<TabIcon icon='/icons/connection.svg' />
<TabTitle><Translate token={configurationWizard ? 'connections_administration_configuration_wizard_step_title' : 'connections_administration_item'} /></TabTitle>
</Tab>
);
}
};
@@ -14,13 +14,13 @@ import {
} from '@cloudbeaver/core-blocks';
import { DBDriverResource } from '@cloudbeaver/core-connections';
import { useService } from '@cloudbeaver/core-di';
import { ConnectionInfo } from '@cloudbeaver/core-sdk';
import { useStyles } from '@cloudbeaver/core-theming';
import { AdminConnection } from '../../ConnectionsResource';
import { ConnectionEdit } from './ConnectionEdit';
interface Props {
connection: ConnectionInfo;
connection: AdminConnection;
}
const styles = css`
@@ -12,10 +12,10 @@ import {
injectable, IInitializableController, IDestructibleController
} from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { GQLErrorCatcher, AdminConnectionGrantInfo, ConnectionInfo } from '@cloudbeaver/core-sdk';
import { GQLErrorCatcher, AdminConnectionGrantInfo } from '@cloudbeaver/core-sdk';
import { DBDriverResource } from '../../../DBDriverResource';
import { ConnectionsResource } from '../../ConnectionsResource';
import { AdminConnection, ConnectionsResource } from '../../ConnectionsResource';
@injectable()
export class ConnectionEditController
@@ -23,7 +23,7 @@ implements IInitializableController, IDestructibleController {
@observable grantedSubjects: AdminConnectionGrantInfo[] | null = null;
@observable isLoading = true;
@observable credentials: Record<string, string> = {};
@observable connection: ConnectionInfo | null = null;
@observable connection: AdminConnection | null = null;
@computed get isDisabled() {
return this.isLoading;
@@ -13,9 +13,9 @@ import {
Table, TableHeader, TableColumnHeader, TableBody
} from '@cloudbeaver/core-blocks';
import { useTranslate } from '@cloudbeaver/core-localization';
import { ConnectionInfo } from '@cloudbeaver/core-sdk';
import { useStyles, composes } from '@cloudbeaver/core-theming';
import { AdminConnection } from '../../ConnectionsResource';
import { Connection } from './Connection';
const styles = composes(
@@ -38,7 +38,7 @@ const styles = composes(
);
interface Props {
connections: ConnectionInfo[];
connections: AdminConnection[];
selectedItems: Map<string, boolean>;
expandedItems: Map<string, boolean>;
}
@@ -10,18 +10,18 @@ import { observable, computed } from 'mobx';
import { injectable } from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { AdminConnectionSearchInfo, ConnectionInfo } from '@cloudbeaver/core-sdk';
import { AdminConnectionSearchInfo } from '@cloudbeaver/core-sdk';
import { uuid } from '@cloudbeaver/core-utils';
import { DBDriverResource } from '../../../DBDriverResource';
import { ConnectionsResource } from '../../ConnectionsResource';
import { AdminConnection, ConnectionsResource } from '../../ConnectionsResource';
@injectable()
export class CreateConnectionController {
@observable hosts = 'localhost';
@observable isProcessing = false;
@observable databases: AdminConnectionSearchInfo[];
@observable connection: ConnectionInfo | null;
@observable connection: AdminConnection | null;
@observable availableDrivers: string[];
@observable credentials: Record<string, string | number>;
@observable grantedSubjects = [];
@@ -77,7 +77,7 @@ export class CreateConnectionController {
template: false,
authProperties: [],
properties: {},
} as Partial<ConnectionInfo> as any;
} as Partial<AdminConnection> as any;
this.availableDrivers = [driverId];
};
@@ -90,7 +90,7 @@ export class CreateConnectionController {
port: `${database.port}`,
authProperties: [],
properties: {},
} as Partial<ConnectionInfo> as any;
} as Partial<AdminConnection> as any;
this.availableDrivers = database.possibleDrivers;
};
@@ -11,7 +11,7 @@ import { Observable, Subject } from 'rxjs';
import { injectable } from '@cloudbeaver/core-di';
import {
GraphQLService,
ConnectionInfo,
AdminConnectionFragment,
ConnectionConfig,
CachedMapResource,
ResourceKey,
@@ -23,22 +23,23 @@ import { MetadataMap } from '@cloudbeaver/core-utils';
export const NEW_CONNECTION_SYMBOL = Symbol('new-connection');
export type ConnectionNew = ConnectionInfo & { [NEW_CONNECTION_SYMBOL]: boolean };
export type AdminConnection = AdminConnectionFragment;
export type ConnectionNew = AdminConnectionFragment & { [NEW_CONNECTION_SYMBOL]: boolean };
@injectable()
export class ConnectionsResource extends CachedMapResource<string, ConnectionInfo> {
readonly onConnectionCreate: Observable<ConnectionInfo>;
export class ConnectionsResource extends CachedMapResource<string, AdminConnection> {
readonly onConnectionCreate: Observable<AdminConnection>;
private changed: boolean;
private metadata: MetadataMap<string, boolean>;
private connectionCreateSubject: Subject<ConnectionInfo>;
private connectionCreateSubject: Subject<AdminConnection>;
constructor(
private graphQLService: GraphQLService
) {
super(new Map());
this.changed = false;
this.connectionCreateSubject = new Subject<ConnectionInfo>();
this.connectionCreateSubject = new Subject<AdminConnection>();
this.onConnectionCreate = this.connectionCreateSubject.asObservable();
this.metadata = new MetadataMap(() => false);
}
@@ -59,7 +60,7 @@ export class ConnectionsResource extends CachedMapResource<string, ConnectionInf
return (connection as ConnectionNew)[NEW_CONNECTION_SYMBOL];
}
async loadAll(): Promise<Map<string, ConnectionInfo>> {
async loadAll(): Promise<Map<string, AdminConnection>> {
await this.load('all');
return this.data;
}
@@ -70,16 +71,16 @@ export class ConnectionsResource extends CachedMapResource<string, ConnectionInf
return databases;
}
async create(config: ConnectionConfig): Promise<ConnectionInfo> {
async create(config: ConnectionConfig): Promise<AdminConnection> {
const { connection } = await this.graphQLService.sdk.createConnectionConfiguration({ config });
return this.add(connection as ConnectionInfo, true);
return this.add(connection, true);
}
async add(connection: ConnectionInfo, isNew = false): Promise<ConnectionInfo> {
async add(connection: AdminConnection, isNew = false): Promise<AdminConnection> {
this.changed = true;
const newConnection: ConnectionNew = {
...connection as ConnectionInfo,
...connection,
[NEW_CONNECTION_SYMBOL]: isNew,
};
this.set(newConnection.id, newConnection);
@@ -95,7 +96,7 @@ export class ConnectionsResource extends CachedMapResource<string, ConnectionInf
});
}
async update(id: string, config: ConnectionConfig): Promise<ConnectionInfo> {
async update(id: string, config: ConnectionConfig): Promise<AdminConnection> {
await this.performUpdate(id, () => this.updateConnection(id, config));
this.changed = true;
return this.get(id)!;
@@ -126,12 +127,12 @@ export class ConnectionsResource extends CachedMapResource<string, ConnectionInf
await this.graphQLService.sdk.setConnectionAccess({ connectionId, subjects });
}
protected async loader(key: ResourceKey<string>): Promise<Map<string, ConnectionInfo>> {
protected async loader(key: ResourceKey<string>): Promise<Map<string, AdminConnection>> {
const { connections } = await this.graphQLService.sdk.getConnections();
this.data.clear();
for (const connection of connections) {
this.set(connection.id, connection as ConnectionInfo);
this.set(connection.id, connection);
}
this.markUpdated(key);
@@ -165,6 +166,6 @@ export class ConnectionsResource extends CachedMapResource<string, ConnectionInf
private async updateConnection(id: string, config: ConnectionConfig) {
const { connection } = await this.graphQLService.sdk.updateConnectionConfiguration({ id, config });
this.set(id, connection as ConnectionInfo);
this.set(id, connection);
}
}
@@ -6,52 +6,39 @@
* you may not use this file except in compliance with the License.
*/
import { Observable, Subject } from 'rxjs';
import { action } from 'mobx';
import { injectable } from '@cloudbeaver/core-di';
import { Executor, IExecutor } from '@cloudbeaver/core-executor';
import { SessionResource } from '@cloudbeaver/core-root';
import {
ConnectionInfo,
UserConnectionFragment,
GraphQLService,
CachedMapResource,
ObjectPropertyInfo,
ConnectionConfig
ConnectionConfig,
UserConnectionAuthPropertiesFragment
} from '@cloudbeaver/core-sdk';
export type Connection = Pick<
ConnectionInfo,
'id' |
'name' |
'description' |
'connected' |
'readOnly' |
'driverId' |
'authModel' |
'authNeeded' |
'features' |
'supportedDataFormats'
> & { authProperties?: ObjectPropertyInfo[] };
export type Connection = UserConnectionFragment & { authProperties?: UserConnectionAuthPropertiesFragment[] };
@injectable()
export class ConnectionInfoResource extends CachedMapResource<string, Connection> {
readonly onConnectionCreate: Observable<Connection>;
private connectionCreateSubject: Subject<Connection>;
readonly onConnectionCreate: IExecutor<Connection>;
constructor(
private graphQLService: GraphQLService,
sessionResource: SessionResource
) {
super(new Map());
this.connectionCreateSubject = new Subject<Connection>();
this.onConnectionCreate = this.connectionCreateSubject.asObservable();
this.onConnectionCreate = new Executor();
sessionResource.onDataUpdate.subscribe(() => this.refreshSession(true));
}
async refreshSession(sessionUpdate?: boolean): Promise<void> {
@action async refreshSession(sessionUpdate?: boolean): Promise<void> {
const { state: { connections } } = await this.graphQLService.sdk.getSessionConnections();
const restoredConnections = new Set<string>();
for (const connection of connections) {
this.add(connection, sessionUpdate);
await this.add(connection, sessionUpdate);
restoredConnections.add(connection.id);
}
@@ -64,32 +51,32 @@ export class ConnectionInfoResource extends CachedMapResource<string, Connection
}
}
async createFromTemplate(templateId: string): Promise<Connection> {
@action async createFromTemplate(templateId: string): Promise<Connection> {
const { connection } = await this.graphQLService.sdk.createConnectionFromTemplate({ templateId });
return this.add(connection);
}
async createConnection(config: ConnectionConfig): Promise<Connection> {
@action async createConnection(config: ConnectionConfig): Promise<Connection> {
const { connection } = await this.graphQLService.sdk.createConnection({
config,
});
return this.add(connection);
}
async createFromNode(nodeId: string): Promise<Connection> {
@action async createFromNode(nodeId: string): Promise<Connection> {
const { connection } = await this.graphQLService.sdk.createConnectionFromNode({ nodePath: nodeId });
return this.add(connection);
}
add(connection: Connection, update?: boolean): Connection {
@action async add(connection: Connection, update?: boolean): Promise<Connection> {
const exists = this.data.has(connection.id);
this.set(connection.id, connection);
const observedConnection = this.get(connection.id)!;
if (!update && !exists) {
this.connectionCreateSubject.next(observedConnection);
await this.onConnectionCreate.execute(observedConnection);
}
return observedConnection;
@@ -121,7 +108,7 @@ export class ConnectionInfoResource extends CachedMapResource<string, Connection
this.delete(connectionId);
}
async loadAuthModel(connectionId: string): Promise<ObjectPropertyInfo[]> {
async loadAuthModel(connectionId: string): Promise<UserConnectionAuthPropertiesFragment[]> {
const connection = await this.load(connectionId);
if (connection?.authProperties) {
@@ -145,7 +132,7 @@ export class ConnectionInfoResource extends CachedMapResource<string, Connection
return this.data;
}
private async getAuthProperties(id: string): Promise<ObjectPropertyInfo[]> {
private async getAuthProperties(id: string): Promise<UserConnectionAuthPropertiesFragment[]> {
const { connection: { authProperties } } = await this.graphQLService.sdk.connectionAuthProperties({ id });
return authProperties;
@@ -106,7 +106,7 @@ export class ConnectionsManagerService {
async closeConnectionAsync(id: string): Promise<void> {
const connection = this.connectionInfo.get(id);
if (!connection) {
if (!connection || !connection.connected) {
return;
}
+3 -3
View File
@@ -6,7 +6,7 @@
* you may not use this file except in compliance with the License.
*/
import { useContext, useMemo } from 'react';
import { useContext } from 'react';
import { appContext } from './AppContext';
import { IServiceConstructor } from './IApp';
@@ -14,10 +14,10 @@ import { ValueToken } from './InjectionToken';
export function useService<T>(ctor: IServiceConstructor<T>): T {
const app = useContext(appContext);
return useMemo(() => app.getServiceByClass(ctor), [app, ctor]);
return app.getServiceByClass(ctor);
}
export function useServiceByToken<T>(token: ValueToken<T>): T {
const app = useContext(appContext);
return useMemo(() => app.getServiceByToken(token), [app, token]);
return app.getServiceByToken(token);
}
@@ -6,14 +6,17 @@
* you may not use this file except in compliance with the License.
*/
export interface IContextProvider<TData> {
export interface IExecutionContextProvider<TData> {
hasContext: (token: IContextLoader<TData>) => boolean;
getContext: <T>(token: IContextLoader<T, TData>) => Promise<T>;
}
export type IContextLoader<T = any, TData = any> = (contexts: IContextProvider<TData>, data: TData) => Promise<T> | T;
export type IContextLoader<T = any, TData = any> = (
contexts: IExecutionContextProvider<TData>,
data: TData
) => Promise<T> | T;
export class ExecutionContext<TData> implements IContextProvider<TData> {
export class ExecutionContext<TData> implements IExecutionContextProvider<TData> {
private contexts = new Map<IContextLoader<any, TData>, any>();
constructor(private data: TData) { }
@@ -6,7 +6,7 @@
* you may not use this file except in compliance with the License.
*/
import { ExecutionContext, IContextProvider } from './ExecutionContext';
import { ExecutionContext, IExecutionContextProvider } from './ExecutionContext';
import { IExecutor } from './IExecutor';
import { IExecutorHandler } from './IExecutorHandler';
@@ -18,7 +18,7 @@ export class Executor<T> implements IExecutor<T> {
private defaultData?: T | null
) { }
async execute(data: T): Promise<IContextProvider<T>> {
async execute(data: T): Promise<IExecutionContextProvider<T>> {
if ((data === undefined || data === null) && this.defaultData !== undefined && this.defaultData !== null) {
data = this.defaultData;
}
@@ -6,11 +6,11 @@
* you may not use this file except in compliance with the License.
*/
import { IContextProvider } from './ExecutionContext';
import { IExecutionContextProvider } from './ExecutionContext';
import { IExecutorHandler } from './IExecutorHandler';
export interface IExecutor<T> {
execute: (data: T) => Promise<IContextProvider<T>>;
execute: (data: T) => Promise<IExecutionContextProvider<T>>;
addHandler: (handler: IExecutorHandler<T>) => void;
removeHandler: (handler: IExecutorHandler<T>) => void;
addPostHandler: (handler: IExecutorHandler<T>) => void;
@@ -6,10 +6,10 @@
* you may not use this file except in compliance with the License.
*/
import { IContextProvider } from './ExecutionContext';
import { IExecutionContextProvider } from './ExecutionContext';
export type IExecutorHandler<T> = (
contexts: IContextProvider<T>,
contexts: IExecutionContextProvider<T>,
data: T
// eslint-disable-next-line @typescript-eslint/no-invalid-void-type
) => void | false | Promise<void | false>;
@@ -12,12 +12,12 @@ import { injectable } from '@cloudbeaver/core-di';
import {
GraphQLService,
CachedDataResource,
SessionInfo
SessionStateFragment
} from '@cloudbeaver/core-sdk';
import { ServerConfigResource } from './ServerConfigResource';
export type SessionState = Pick<SessionInfo, 'createTime' | 'cacheExpired' | 'lastAccessTime' | 'locale'>;
export type SessionState = SessionStateFragment;
@injectable()
export class SessionResource extends CachedDataResource<SessionState | null, null> {
@@ -1,29 +1,5 @@
query createConnectionConfiguration($config: ConnectionConfig!) {
connection: createConnectionConfiguration(config: $config) {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
features
authNeeded
authModel
authProperties {
id
value
features
}
...AdminConnection
}
}
@@ -1,29 +1,5 @@
query createConnectionConfigurationFromNode($nodePath: String!) {
connection: copyConnectionConfiguration(nodePath: $nodePath) {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
features
authNeeded
authModel
authProperties {
id
value
features
}
...AdminConnection
}
}
@@ -1,30 +1,5 @@
query getConnections {
connections: allConnections {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
authNeeded
authModel
authProperties {
id
value
features
}
features
supportedDataFormats
...AdminConnection
}
}
@@ -1,30 +1,5 @@
query updateConnectionConfiguration($id: ID!, $config: ConnectionConfig!) {
connection: updateConnectionConfiguration(id: $id, config: $config) {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
authNeeded
authModel
authProperties {
id
value
features
}
features
supportedDataFormats
...AdminConnection
}
}
@@ -1,16 +1,5 @@
mutation closeConnection($id: ID!) {
connection: closeConnection(id: $id) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
@@ -1,15 +1,7 @@
query connectionAuthProperties($id: ID!) {
connection: connectionInfo(id: $id) {
authProperties {
id
displayName
description
category
dataType
value
validValues
defaultValue
features
...UserConnectionAuthProperties
}
}
}
@@ -1,16 +1,5 @@
query connectionInfo($id: ID!) {
connection: connectionInfo(id: $id) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
@@ -1,16 +1,5 @@
mutation createConnection($config: ConnectionConfig!) {
connection: createConnection(config: $config) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
@@ -1,16 +1,5 @@
mutation createConnectionFromNode($nodePath: String!) {
connection: copyConnectionFromNode(nodePath: $nodePath) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
@@ -1,16 +1,5 @@
mutation createConnectionFromTemplate($templateId: ID!) {
connection: createConnectionFromTemplate(templateId: $templateId) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
@@ -1,16 +1,5 @@
mutation initConnection($id: ID!, $credentials: Object) {
connection: initConnection(id: $id, credentials: $credentials) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
@@ -0,0 +1,30 @@
fragment AdminConnection on ConnectionInfo {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
features
authNeeded
authModel
authProperties {
id
value
features
}
features
supportedDataFormats
}
@@ -0,0 +1,14 @@
fragment NavNodeInfo on NavigatorNodeInfo {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
}
@@ -0,0 +1,9 @@
fragment NavNodeProperties on ObjectPropertyInfo {
id
category
dataType
description
displayName
features
value
}
@@ -0,0 +1,6 @@
fragment SessionState on SessionInfo {
createTime
lastAccessTime
cacheExpired
locale
}
@@ -0,0 +1,14 @@
fragment UserConnection on ConnectionInfo {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
}
@@ -0,0 +1,11 @@
fragment UserConnectionAuthProperties on ObjectPropertyInfo {
id
displayName
description
category
dataType
value
validValues
defaultValue
features
}
@@ -7,13 +7,7 @@ query getChildrenDBObjectInfo(
object {
features
properties(filter: $filter) {
id
category
dataType
description
displayName
features
value
...NavNodeProperties
}
}
}
@@ -3,13 +3,7 @@ query getDBObjectInfo($navNodeId: ID!, $filter: ObjectPropertyFilter) {
object {
features
properties(filter: $filter) {
id
category
dataType
description
displayName
features
value
...NavNodeProperties
}
}
}
@@ -1,31 +1,9 @@
query navNodeChildren($parentPath: ID!) {
navNodeChildren(parentPath: $parentPath) {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
...NavNodeInfo
}
navNodeInfo(nodePath: $parentPath) {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
...NavNodeInfo
}
}
@@ -1,16 +1,5 @@
query navNodeInfo($nodePath: ID!) {
navNodeInfo(nodePath: $nodePath) {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
...NavNodeInfo
}
}
@@ -1,18 +1,7 @@
query getSessionConnections {
state: sessionState {
connections {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
}
@@ -1,8 +1,5 @@
mutation openSession {
session: openSession {
createTime
lastAccessTime
cacheExpired
locale
...SessionState
}
}
@@ -1,20 +1,5 @@
query sessionState {
sessionState {
createTime
lastAccessTime
locale
cacheExpired
connections {
id
name
driverId
connected
authNeeded
authModel
features
supportedDataFormats
}
...SessionState
}
}
+162 -307
View File
@@ -943,23 +943,13 @@ export type CreateConnectionConfigurationQueryVariables = Exact<{
config: ConnectionConfig;
}>;
export interface CreateConnectionConfigurationQuery {
connection: (
Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'template' | 'connected' | 'readOnly' | 'saveCredentials' | 'host' | 'port' | 'databaseName' | 'url' | 'properties' | 'features' | 'authNeeded' | 'authModel'>
& { authProperties: Array<Pick<ObjectPropertyInfo, 'id' | 'value' | 'features'>> }
);
}
export interface CreateConnectionConfigurationQuery { connection: AdminConnectionFragment }
export type CreateConnectionConfigurationFromNodeQueryVariables = Exact<{
nodePath: Scalars['String'];
}>;
export interface CreateConnectionConfigurationFromNodeQuery {
connection: (
Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'template' | 'connected' | 'readOnly' | 'saveCredentials' | 'host' | 'port' | 'databaseName' | 'url' | 'properties' | 'features' | 'authNeeded' | 'authModel'>
& { authProperties: Array<Pick<ObjectPropertyInfo, 'id' | 'value' | 'features'>> }
);
}
export interface CreateConnectionConfigurationFromNodeQuery { connection: AdminConnectionFragment }
export type DeleteConnectionConfigurationQueryVariables = Exact<{
id: Scalars['ID'];
@@ -975,12 +965,7 @@ export interface GetConnectionAccessQuery { subjects: Array<Pick<AdminConnection
export type GetConnectionsQueryVariables = Exact<{ [key: string]: never }>;
export interface GetConnectionsQuery {
connections: Array<(
Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'template' | 'connected' | 'readOnly' | 'saveCredentials' | 'host' | 'port' | 'databaseName' | 'url' | 'properties' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'>
& { authProperties: Array<Pick<ObjectPropertyInfo, 'id' | 'value' | 'features'>> }
)>;
}
export interface GetConnectionsQuery { connections: AdminConnectionFragment[] }
export type SearchDatabasesQueryVariables = Exact<{
hosts: Array<Scalars['String']>;
@@ -1000,48 +985,43 @@ export type UpdateConnectionConfigurationQueryVariables = Exact<{
config: ConnectionConfig;
}>;
export interface UpdateConnectionConfigurationQuery {
connection: (
Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'template' | 'connected' | 'readOnly' | 'saveCredentials' | 'host' | 'port' | 'databaseName' | 'url' | 'properties' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'>
& { authProperties: Array<Pick<ObjectPropertyInfo, 'id' | 'value' | 'features'>> }
);
}
export interface UpdateConnectionConfigurationQuery { connection: AdminConnectionFragment }
export type CloseConnectionMutationVariables = Exact<{
id: Scalars['ID'];
}>;
export interface CloseConnectionMutation { connection: Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'> }
export interface CloseConnectionMutation { connection: UserConnectionFragment }
export type ConnectionAuthPropertiesQueryVariables = Exact<{
id: Scalars['ID'];
}>;
export interface ConnectionAuthPropertiesQuery { connection: { authProperties: Array<Pick<ObjectPropertyInfo, 'id' | 'displayName' | 'description' | 'category' | 'dataType' | 'value' | 'validValues' | 'defaultValue' | 'features'>> } }
export interface ConnectionAuthPropertiesQuery { connection: { authProperties: UserConnectionAuthPropertiesFragment[] } }
export type ConnectionInfoQueryVariables = Exact<{
id: Scalars['ID'];
}>;
export interface ConnectionInfoQuery { connection: Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'> }
export interface ConnectionInfoQuery { connection: UserConnectionFragment }
export type CreateConnectionMutationVariables = Exact<{
config: ConnectionConfig;
}>;
export interface CreateConnectionMutation { connection: Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'> }
export interface CreateConnectionMutation { connection: UserConnectionFragment }
export type CreateConnectionFromNodeMutationVariables = Exact<{
nodePath: Scalars['String'];
}>;
export interface CreateConnectionFromNodeMutation { connection: Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'> }
export interface CreateConnectionFromNodeMutation { connection: UserConnectionFragment }
export type CreateConnectionFromTemplateMutationVariables = Exact<{
templateId: Scalars['ID'];
}>;
export interface CreateConnectionFromTemplateMutation { connection: Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'> }
export interface CreateConnectionFromTemplateMutation { connection: UserConnectionFragment }
export type DeleteConnectionMutationVariables = Exact<{
id: Scalars['ID'];
@@ -1084,7 +1064,7 @@ export type InitConnectionMutationVariables = Exact<{
credentials?: Maybe<Scalars['Object']>;
}>;
export interface InitConnectionMutation { connection: Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'> }
export interface InitConnectionMutation { connection: UserConnectionFragment }
export type RefreshSessionConnectionsMutationVariables = Exact<{ [key: string]: never }>;
@@ -1149,6 +1129,24 @@ export type NavGetStructContainersQueryVariables = Exact<{
export interface NavGetStructContainersQuery { navGetStructContainers: { catalogList: Array<Pick<DatabaseObjectInfo, 'name' | 'description' | 'type' | 'features'>>; schemaList: Array<Pick<DatabaseObjectInfo, 'name' | 'description' | 'type' | 'features'>> } }
export type AdminConnectionFragment = (
Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'template' | 'connected' | 'readOnly' | 'saveCredentials' | 'host' | 'port' | 'databaseName' | 'url' | 'properties' | 'features' | 'authNeeded' | 'authModel' | 'supportedDataFormats'>
& { authProperties: Array<Pick<ObjectPropertyInfo, 'id' | 'value' | 'features'>> }
);
export type NavNodeInfoFragment = (
Pick<NavigatorNodeInfo, 'id' | 'name' | 'hasChildren' | 'nodeType' | 'icon' | 'folder' | 'inline' | 'navigable' | 'features'>
& { object?: Maybe<Pick<DatabaseObjectInfo, 'features'>> }
);
export type NavNodePropertiesFragment = Pick<ObjectPropertyInfo, 'id' | 'category' | 'dataType' | 'description' | 'displayName' | 'features' | 'value'>;
export type SessionStateFragment = Pick<SessionInfo, 'createTime' | 'lastAccessTime' | 'cacheExpired' | 'locale'>;
export type UserConnectionFragment = Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'>;
export type UserConnectionAuthPropertiesFragment = Pick<ObjectPropertyInfo, 'id' | 'displayName' | 'description' | 'category' | 'dataType' | 'value' | 'validValues' | 'defaultValue' | 'features'>;
export type GetAsyncTaskInfoMutationVariables = Exact<{
taskId: Scalars['String'];
removeOnFinish: Scalars['Boolean'];
@@ -1267,7 +1265,7 @@ export interface GetChildrenDbObjectInfoQuery {
Pick<NavigatorNodeInfo, 'id'>
& { object?: Maybe<(
Pick<DatabaseObjectInfo, 'features'>
& { properties?: Maybe<Array<Maybe<Pick<ObjectPropertyInfo, 'id' | 'category' | 'dataType' | 'description' | 'displayName' | 'features' | 'value'>>>> }
& { properties?: Maybe<Array<Maybe<NavNodePropertiesFragment>>> }
)>; }
)>;
}
@@ -1280,7 +1278,7 @@ export type GetDbObjectInfoQueryVariables = Exact<{
export interface GetDbObjectInfoQuery {
objectInfo: { object?: Maybe<(
Pick<DatabaseObjectInfo, 'features'>
& { properties?: Maybe<Array<Maybe<Pick<ObjectPropertyInfo, 'id' | 'category' | 'dataType' | 'description' | 'displayName' | 'features' | 'value'>>>> }
& { properties?: Maybe<Array<Maybe<NavNodePropertiesFragment>>> }
)>; };
}
@@ -1288,26 +1286,13 @@ export type NavNodeChildrenQueryVariables = Exact<{
parentPath: Scalars['ID'];
}>;
export interface NavNodeChildrenQuery {
navNodeChildren: Array<(
Pick<NavigatorNodeInfo, 'id' | 'name' | 'hasChildren' | 'nodeType' | 'icon' | 'folder' | 'inline' | 'navigable' | 'features'>
& { object?: Maybe<Pick<DatabaseObjectInfo, 'features'>> }
)>; navNodeInfo: (
Pick<NavigatorNodeInfo, 'id' | 'name' | 'hasChildren' | 'nodeType' | 'icon' | 'folder' | 'inline' | 'navigable' | 'features'>
& { object?: Maybe<Pick<DatabaseObjectInfo, 'features'>> }
);
}
export interface NavNodeChildrenQuery { navNodeChildren: NavNodeInfoFragment[]; navNodeInfo: NavNodeInfoFragment }
export type NavNodeInfoQueryVariables = Exact<{
nodePath: Scalars['ID'];
}>;
export interface NavNodeInfoQuery {
navNodeInfo: (
Pick<NavigatorNodeInfo, 'id' | 'name' | 'hasChildren' | 'nodeType' | 'icon' | 'folder' | 'inline' | 'navigable' | 'features'>
& { object?: Maybe<Pick<DatabaseObjectInfo, 'features'>> }
);
}
export interface NavNodeInfoQuery { navNodeInfo: NavNodeInfoFragment }
export type NavRefreshNodeQueryVariables = Exact<{
nodePath: Scalars['ID'];
@@ -1351,11 +1336,11 @@ export type ChangeSessionLanguageMutation = Pick<Mutation, 'changeSessionLanguag
export type GetSessionConnectionsQueryVariables = Exact<{ [key: string]: never }>;
export interface GetSessionConnectionsQuery { state: { connections: Array<Pick<ConnectionInfo, 'id' | 'name' | 'description' | 'driverId' | 'connected' | 'readOnly' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'>> } }
export interface GetSessionConnectionsQuery { state: { connections: UserConnectionFragment[] } }
export type OpenSessionMutationVariables = Exact<{ [key: string]: never }>;
export interface OpenSessionMutation { session: Pick<SessionInfo, 'createTime' | 'lastAccessTime' | 'cacheExpired' | 'locale'> }
export interface OpenSessionMutation { session: SessionStateFragment }
export type ReadSessionLogQueryVariables = Exact<{
maxEntries: Scalars['Int'];
@@ -1379,12 +1364,7 @@ export interface SessionPermissionsQuery { permissions: Query['sessionPermission
export type SessionStateQueryVariables = Exact<{ [key: string]: never }>;
export interface SessionStateQuery {
sessionState: (
Pick<SessionInfo, 'createTime' | 'lastAccessTime' | 'locale' | 'cacheExpired'>
& { connections: Array<Pick<ConnectionInfo, 'id' | 'name' | 'driverId' | 'connected' | 'authNeeded' | 'authModel' | 'features' | 'supportedDataFormats'>> }
);
}
export interface SessionStateQuery { sessionState: SessionStateFragment }
export type TouchSessionMutationVariables = Exact<{ [key: string]: never }>;
@@ -1422,6 +1402,95 @@ export type SqlResultCloseMutationVariables = Exact<{
export interface SqlResultCloseMutation { result: Mutation['sqlResultClose'] }
export const AdminConnectionFragmentDoc = `
fragment AdminConnection on ConnectionInfo {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
features
authNeeded
authModel
authProperties {
id
value
features
}
features
supportedDataFormats
}
`;
export const NavNodeInfoFragmentDoc = `
fragment NavNodeInfo on NavigatorNodeInfo {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
}
`;
export const NavNodePropertiesFragmentDoc = `
fragment NavNodeProperties on ObjectPropertyInfo {
id
category
dataType
description
displayName
features
value
}
`;
export const SessionStateFragmentDoc = `
fragment SessionState on SessionInfo {
createTime
lastAccessTime
cacheExpired
locale
}
`;
export const UserConnectionFragmentDoc = `
fragment UserConnection on ConnectionInfo {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
}
`;
export const UserConnectionAuthPropertiesFragmentDoc = `
fragment UserConnectionAuthProperties on ObjectPropertyInfo {
id
displayName
description
category
dataType
value
validValues
defaultValue
features
}
`;
export const AsyncTaskCancelDocument = `
mutation asyncTaskCancel($taskId: String!) {
result: asyncTaskCancel(id: $taskId)
@@ -1546,57 +1615,17 @@ export const SetUserCredentialsDocument = `
export const CreateConnectionConfigurationDocument = `
query createConnectionConfiguration($config: ConnectionConfig!) {
connection: createConnectionConfiguration(config: $config) {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
features
authNeeded
authModel
authProperties {
id
value
features
}
...AdminConnection
}
}
`;
${AdminConnectionFragmentDoc}`;
export const CreateConnectionConfigurationFromNodeDocument = `
query createConnectionConfigurationFromNode($nodePath: String!) {
connection: copyConnectionConfiguration(nodePath: $nodePath) {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
features
authNeeded
authModel
authProperties {
id
value
features
}
...AdminConnection
}
}
`;
${AdminConnectionFragmentDoc}`;
export const DeleteConnectionConfigurationDocument = `
query deleteConnectionConfiguration($id: ID!) {
deleteConnectionConfiguration(id: $id)
@@ -1614,31 +1643,10 @@ export const GetConnectionAccessDocument = `
export const GetConnectionsDocument = `
query getConnections {
connections: allConnections {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
authNeeded
authModel
authProperties {
id
value
features
}
features
supportedDataFormats
...AdminConnection
}
}
`;
${AdminConnectionFragmentDoc}`;
export const SearchDatabasesDocument = `
query searchDatabases($hosts: [String!]!) {
databases: searchConnections(hostNames: $hosts) {
@@ -1658,128 +1666,54 @@ export const SetConnectionAccessDocument = `
export const UpdateConnectionConfigurationDocument = `
query updateConnectionConfiguration($id: ID!, $config: ConnectionConfig!) {
connection: updateConnectionConfiguration(id: $id, config: $config) {
id
name
description
driverId
template
connected
readOnly
saveCredentials
host
port
databaseName
url
properties
authNeeded
authModel
authProperties {
id
value
features
}
features
supportedDataFormats
...AdminConnection
}
}
`;
${AdminConnectionFragmentDoc}`;
export const CloseConnectionDocument = `
mutation closeConnection($id: ID!) {
connection: closeConnection(id: $id) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
`;
${UserConnectionFragmentDoc}`;
export const ConnectionAuthPropertiesDocument = `
query connectionAuthProperties($id: ID!) {
connection: connectionInfo(id: $id) {
authProperties {
id
displayName
description
category
dataType
value
validValues
defaultValue
features
...UserConnectionAuthProperties
}
}
}
`;
${UserConnectionAuthPropertiesFragmentDoc}`;
export const ConnectionInfoDocument = `
query connectionInfo($id: ID!) {
connection: connectionInfo(id: $id) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
`;
${UserConnectionFragmentDoc}`;
export const CreateConnectionDocument = `
mutation createConnection($config: ConnectionConfig!) {
connection: createConnection(config: $config) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
`;
${UserConnectionFragmentDoc}`;
export const CreateConnectionFromNodeDocument = `
mutation createConnectionFromNode($nodePath: String!) {
connection: copyConnectionFromNode(nodePath: $nodePath) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
`;
${UserConnectionFragmentDoc}`;
export const CreateConnectionFromTemplateDocument = `
mutation createConnectionFromTemplate($templateId: ID!) {
connection: createConnectionFromTemplate(templateId: $templateId) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
`;
${UserConnectionFragmentDoc}`;
export const DeleteConnectionDocument = `
mutation deleteConnection($id: ID!) {
deleteConnection(id: $id)
@@ -1852,19 +1786,10 @@ export const GetDriverByIdDocument = `
export const InitConnectionDocument = `
mutation initConnection($id: ID!, $credentials: Object) {
connection: initConnection(id: $id, credentials: $credentials) {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
`;
${UserConnectionFragmentDoc}`;
export const RefreshSessionConnectionsDocument = `
mutation refreshSessionConnections {
refreshSessionConnections
@@ -2108,86 +2033,41 @@ export const GetChildrenDbObjectInfoDocument = `
object {
features
properties(filter: $filter) {
id
category
dataType
description
displayName
features
value
...NavNodeProperties
}
}
}
}
`;
${NavNodePropertiesFragmentDoc}`;
export const GetDbObjectInfoDocument = `
query getDBObjectInfo($navNodeId: ID!, $filter: ObjectPropertyFilter) {
objectInfo: navNodeInfo(nodePath: $navNodeId) {
object {
features
properties(filter: $filter) {
id
category
dataType
description
displayName
features
value
...NavNodeProperties
}
}
}
}
`;
${NavNodePropertiesFragmentDoc}`;
export const NavNodeChildrenDocument = `
query navNodeChildren($parentPath: ID!) {
navNodeChildren(parentPath: $parentPath) {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
...NavNodeInfo
}
navNodeInfo(nodePath: $parentPath) {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
...NavNodeInfo
}
}
`;
${NavNodeInfoFragmentDoc}`;
export const NavNodeInfoDocument = `
query navNodeInfo($nodePath: ID!) {
navNodeInfo(nodePath: $nodePath) {
id
name
hasChildren
nodeType
icon
folder
inline
navigable
features
object {
features
}
...NavNodeInfo
}
}
`;
${NavNodeInfoFragmentDoc}`;
export const NavRefreshNodeDocument = `
query navRefreshNode($nodePath: ID!) {
navRefreshNode(nodePath: $nodePath)
@@ -2243,30 +2123,18 @@ export const GetSessionConnectionsDocument = `
query getSessionConnections {
state: sessionState {
connections {
id
name
description
driverId
connected
readOnly
authNeeded
authModel
features
supportedDataFormats
...UserConnection
}
}
}
`;
${UserConnectionFragmentDoc}`;
export const OpenSessionDocument = `
mutation openSession {
session: openSession {
createTime
lastAccessTime
cacheExpired
locale
...SessionState
}
}
`;
${SessionStateFragmentDoc}`;
export const ReadSessionLogDocument = `
query readSessionLog($maxEntries: Int!, $clearEntries: Boolean!) {
log: readSessionLog(maxEntries: $maxEntries, clearEntries: $clearEntries) {
@@ -2317,23 +2185,10 @@ export const SessionPermissionsDocument = `
export const SessionStateDocument = `
query sessionState {
sessionState {
createTime
lastAccessTime
locale
cacheExpired
connections {
id
name
driverId
connected
authNeeded
authModel
features
supportedDataFormats
}
...SessionState
}
}
`;
${SessionStateFragmentDoc}`;
export const TouchSessionDocument = `
mutation touchSession {
touchSession
@@ -14,18 +14,24 @@ import { useStyles, composes } from '@cloudbeaver/core-theming';
import { UserForm } from './UserForm/UserForm';
interface Props {
user: AdminUserInfo;
onCancel: () => void;
}
const styles = composes(
css`
title-bar {
composes: theme-border-color-background from global;
}
user-create-footer, user-create-content {
composes: theme-background-secondary theme-text-on-secondary from global;
}
`,
css`
user-create {
display: flex;
flex-direction: column;
height: 500px;
overflow: hidden;
}
title-bar {
composes: theme-typography--headline6 from global;
box-sizing: border-box;
@@ -36,17 +42,38 @@ const styles = composes(
font-weight: 400;
flex: auto 0 0;
}
user-create-footer {
padding-bottom: 48px;
flex: auto 0 0;
}
user-create-content {
position: relative;
display: flex;
flex-direction: column;
flex: 1;
overflow: auto;
}
`
);
export function CreateUser({
interface Props {
user: AdminUserInfo;
onCancel: () => void;
}
export const CreateUser: React.FC<Props> = function CreateUser({
user,
onCancel,
}: Props) {
}) {
return styled(useStyles(styles))(
<user-create as='div'>
<title-bar as='div'><Translate token='authentication_administration_user_connections_user_add' /></title-bar>
<UserForm user={user} onCancel={onCancel} />
<user-create-content as='div'>
<UserForm user={user} onCancel={onCancel} />
</user-create-content>
<user-create-footer as='div' />
</user-create>
);
}
};
@@ -14,10 +14,10 @@ import {
Table, TableHeader, TableColumnHeader, TableBody,
TableItem, TableColumnValue, TableItemSelect, StaticImage, TextPlaceholder
} from '@cloudbeaver/core-blocks';
import { DBDriverResource } from '@cloudbeaver/core-connections';
import { AdminConnection, DBDriverResource } from '@cloudbeaver/core-connections';
import { useService } from '@cloudbeaver/core-di';
import { useTranslate } from '@cloudbeaver/core-localization';
import { AdminSubjectType, ConnectionInfo, AdminConnectionGrantInfo } from '@cloudbeaver/core-sdk';
import { AdminSubjectType, AdminConnectionGrantInfo } from '@cloudbeaver/core-sdk';
import { useStyles, composes } from '@cloudbeaver/core-theming';
const styles = composes(
@@ -42,7 +42,7 @@ const styles = composes(
interface Props {
grantedConnections: AdminConnectionGrantInfo[];
connections: ConnectionInfo[];
connections: AdminConnection[];
selectedConnection: Map<string, boolean>;
disabled: boolean;
onChange?: () => void;
@@ -54,6 +54,21 @@ const styles = composes(
}
`,
css`
box {
display: flex;
flex-direction: column;
flex: 1;
height: 100%;
overflow: auto;
}
content-box {
display: flex;
flex: 1;
flex-direction: column;
overflow: auto;
}
SubmittingForm {
flex: 1;
display: flex;
@@ -22,7 +22,7 @@ export default [
['authentication_user_password', 'User password'],
['authentication_user_password_repeat', 'Repeat password'],
['authentication_user_role', 'User role'],
['authentication_user_login_not_set', 'Login cant\'t be empty'],
['authentication_user_login_not_set', 'Login can\'t be empty'],
['authentication_user_role_not_set', 'At least one role must be selected'],
['authentication_user_password_not_set', 'Password is required'],
['authentication_user_passwords_not_match', "Passwords don't match"],
@@ -14,7 +14,7 @@ import {
} from '@cloudbeaver/core-app';
import { injectable } from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { IContextProvider } from '@cloudbeaver/core-executor';
import { IExecutionContextProvider } from '@cloudbeaver/core-executor';
import {
DBObjectPageService, ObjectPage, ObjectViewerTabService, IObjectViewerTabState
} from '@cloudbeaver/plugin-object-viewer';
@@ -51,7 +51,7 @@ export class DataViewerTabService {
this.navNodeManagerService.navigator.addHandler(this.navigationHandler.bind(this));
}
private async navigationHandler(contexts: IContextProvider<INodeNavigationData>) {
private async navigationHandler(contexts: IExecutionContextProvider<INodeNavigationData>) {
try {
const {
nodeInfo,
@@ -12,7 +12,7 @@ import {
import { ITab } from '@cloudbeaver/core-blocks';
import { injectable } from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { IContextProvider } from '@cloudbeaver/core-executor';
import { IExecutionContextProvider } from '@cloudbeaver/core-executor';
import { ObjectViewerTabService } from '@cloudbeaver/plugin-object-viewer';
import { ddlViewer } from './DdlViewer/DdlViewer';
@@ -47,7 +47,7 @@ export class DdlViewerTabService {
return ddlTab;
}
private async navigationHandler(contexts: IContextProvider<INodeNavigationData>) {
private async navigationHandler(contexts: IExecutionContextProvider<INodeNavigationData>) {
try {
const tabContext = await contexts.getContext(this.objectViewerTabService.objectViewerTabContext);
@@ -11,7 +11,7 @@ import {
} from '@cloudbeaver/core-app';
import { injectable } from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { IContextProvider } from '@cloudbeaver/core-executor';
import { IExecutionContextProvider } from '@cloudbeaver/core-executor';
import { IObjectViewerTabState } from '../IObjectViewerTabState';
import { DBObjectPageService } from '../ObjectPage/DBObjectPageService';
@@ -50,7 +50,7 @@ export class ObjectPropertiesPageService {
// await this.nodesManagerService.loadNodeInfo(tab.handlerState.objectId);
}
private async navigationHandler(contexts: IContextProvider<INodeNavigationData>) {
private async navigationHandler(contexts: IExecutionContextProvider<INodeNavigationData>) {
if (!this.page) { // TODO: it will be never true, because navHandler registers after page creation
return;
}
@@ -22,7 +22,7 @@ import {
import { connectionProvider, ConnectionInfoResource } from '@cloudbeaver/core-connections';
import { injectable } from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { IContextProvider } from '@cloudbeaver/core-executor';
import { IExecutionContextProvider } from '@cloudbeaver/core-executor';
import { ResourceKey, resourceKeyList, isResourceKeyList } from '@cloudbeaver/core-sdk';
import { IObjectViewerTabContext } from './IObjectViewerTabContext';
@@ -74,7 +74,7 @@ export class ObjectViewerTabService {
}
objectViewerTabContext = async (
contexts: IContextProvider<INodeNavigationData>,
contexts: IExecutionContextProvider<INodeNavigationData>,
data: INodeNavigationData
): Promise<IObjectViewerTabContext> => {
const tabInfo = await contexts.getContext(this.navigationTabsService.navigationTabContext);
@@ -308,7 +308,7 @@ export class ObjectViewerTabService {
await this.dbObjectPageService.closePages(tab);
}
private async navigationHandler(contexts: IContextProvider<INodeNavigationData>) {
private async navigationHandler(contexts: IExecutionContextProvider<INodeNavigationData>) {
try {
const { tab, tabInfo, nodeInfo } = await contexts.getContext(this.objectViewerTabContext);
@@ -10,7 +10,7 @@ import { NavigationTabsService } from '@cloudbeaver/core-app';
import { ConnectionsManagerService, ConnectionInfoResource } from '@cloudbeaver/core-connections';
import { injectable } from '@cloudbeaver/core-di';
import { NotificationService } from '@cloudbeaver/core-events';
import { IExecutor, Executor, IContextProvider } from '@cloudbeaver/core-executor';
import { IExecutor, Executor, IExecutionContextProvider } from '@cloudbeaver/core-executor';
import { SqlEditorTabService, isSQLEditorTab } from './SqlEditorTabService';
import { SqlExecutionState } from './SqlExecutionState';
@@ -97,7 +97,7 @@ export class SqlEditorNavigatorService {
}
private async navigateHandler(
contexts: IContextProvider<SQLCreateAction | SQLEditorAction>,
contexts: IExecutionContextProvider<SQLCreateAction | SQLEditorAction>,
data: SQLCreateAction | SQLEditorAction
) {
try {