Skip to content

Commit

Permalink
Merge branch 'devel' into CB-5340-unit-tests-for-basic-core-blocks-hooks
Browse files Browse the repository at this point in the history
  • Loading branch information
sergeyteleshev committed Jul 17, 2024
2 parents 2b1795a + 75fdc2b commit c52a992
Show file tree
Hide file tree
Showing 216 changed files with 1,904 additions and 1,781 deletions.
19 changes: 4 additions & 15 deletions .vscode/tasks.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,27 +34,16 @@
}
},
{
"label": "Generate dev proprties for CBCE",
"label": "Generate Eclipse PDE CloudBeaver",
"type": "shell",
"command": "mvn",
"osx": {
"args": [
"package",
"-q",
"exec:java",
"-Dexec.args= -eclipse.version ${eclipse-version} -config ${workspaceFolder}/../idea-workspace-dbeaver/osgi-app.properties -productFile ${workspaceFolder}/server/product/web-server/CloudbeaverServer.product -projectsFolder ${workspaceFolder}/../ -eclipse ${workspaceFolder}/../dbeaver-workspace/dependencies -output ${workspaceFolder}/../dbeaver-workspace/products/CloudbeaverServer.product"
]
"command": "./generate_workspace.sh"
},
"windows": {
"args": [
"package",
"-q",
"exec:java",
"-Dexec.args= -eclipse.version ${eclipse-version} -config ${workspaceFolder}/../cloudbeaver/osgi-app.properties"
]
"command": "./generate_workspace.cmd"
},
"options": {
"cwd": "${workspaceFolder}/../idea-rcp-launch-config-generator"
"cwd": "${workspaceFolder}/../cloudbeaver"
},
"presentation": {
"reveal": "silent",
Expand Down
2 changes: 1 addition & 1 deletion apps/h2-query-executor/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>2.2.220</version>
<version>2.1.214</version>
</dependency>
</dependencies>
<build>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,12 +24,11 @@
import io.cloudbeaver.utils.CBModelConstants;
import io.cloudbeaver.utils.WebAppUtils;
import io.cloudbeaver.utils.WebCommonUtils;
import org.jkiss.code.NotNull;
import org.jkiss.dbeaver.DBException;
import org.jkiss.dbeaver.Log;
import org.jkiss.dbeaver.model.DBConstants;
import org.jkiss.dbeaver.model.DBPDataSource;
import org.jkiss.dbeaver.model.DBPDataSourceContainer;
import org.jkiss.dbeaver.model.DBPDataSourceFolder;
import org.jkiss.dbeaver.model.*;
import org.jkiss.dbeaver.model.admin.sessions.DBAServerSessionManager;
import org.jkiss.dbeaver.model.app.DBPProject;
import org.jkiss.dbeaver.model.connection.DBPAuthModelDescriptor;
import org.jkiss.dbeaver.model.connection.DBPConnectionConfiguration;
Expand All @@ -40,6 +39,7 @@
import org.jkiss.dbeaver.model.navigator.DBNDataSource;
import org.jkiss.dbeaver.model.preferences.DBPPropertyDescriptor;
import org.jkiss.dbeaver.model.preferences.DBPPropertySource;
import org.jkiss.dbeaver.model.rm.RMConstants;
import org.jkiss.dbeaver.model.rm.RMProjectPermission;
import org.jkiss.dbeaver.model.runtime.DBRRunnableParametrized;
import org.jkiss.dbeaver.runtime.DBWorkbench;
Expand All @@ -56,6 +56,17 @@ public class WebConnectionInfo {

private static final Log log = Log.getLog(WebConnectionInfo.class);
public static final String SECURED_VALUE = "********";

private static final String FEATURE_HAS_TOOLS = "hasTools";
private static final String FEATURE_CONNECTED = "connected";
private static final String FEATURE_VIRTUAL = "virtual";
private static final String FEATURE_TEMPORARY = "temporary";
private static final String FEATURE_READ_ONLY = "readOnly";
private static final String FEATURE_PROVIDED = "provided";
private static final String FEATURE_MANAGEABLE = "manageable";

private static final String TOOL_SESSION_MANAGER = "sessionManager";

private final WebSession session;
private final DBPDataSourceContainer dataSourceContainer;
private WebServerError connectError;
Expand Down Expand Up @@ -243,22 +254,25 @@ public String[] getFeatures() {
List<String> features = new ArrayList<>();

if (dataSourceContainer.isConnected()) {
features.add("connected");
features.add(FEATURE_CONNECTED);
if (!getTools().isEmpty()) {
features.add(FEATURE_HAS_TOOLS);
}
}
if (dataSourceContainer.isHidden()) {
features.add("virtual");
features.add(FEATURE_VIRTUAL);
}
if (dataSourceContainer.isTemporary()) {
features.add("temporary");
features.add(FEATURE_TEMPORARY);
}
if (dataSourceContainer.isConnectionReadOnly()) {
features.add("readOnly");
features.add(FEATURE_READ_ONLY);
}
if (dataSourceContainer.isProvided()) {
features.add("provided");
features.add(FEATURE_PROVIDED);
}
if (dataSourceContainer.isManageable()) {
features.add("manageable");
features.add(FEATURE_MANAGEABLE);
}

return features.toArray(new String[0]);
Expand Down Expand Up @@ -475,4 +489,18 @@ public List<WebSecretInfo> getSharedSecrets() throws DBException {
.collect(Collectors.toList());
}

@NotNull
@Property
public List<String> getTools() {
if (!session.hasPermission(RMConstants.PERMISSION_DATABASE_DEVELOPER)) {
return List.of();
}
List<String> tools = new ArrayList<>();
// checks inside that datasource is not null in container, and it is adaptable to session manager class
if (DBUtils.getAdapter(DBAServerSessionManager.class, dataSourceContainer) != null) {
tools.add(TOOL_SESSION_MANAGER);
}
return tools;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -401,6 +401,8 @@ type ConnectionInfo {

projectId: ID!
requiredAuth: String

tools: [String!]! @since(version: "24.1.3")
}

type ConnectionFolderInfo {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,13 +21,15 @@
import com.google.gson.InstanceCreator;
import io.cloudbeaver.model.WebConnectionConfig;
import io.cloudbeaver.model.WebNetworkHandlerConfigInput;
import io.cloudbeaver.model.WebPropertyInfo;
import io.cloudbeaver.model.session.WebActionParameters;
import io.cloudbeaver.model.session.WebSession;
import io.cloudbeaver.registry.WebAuthProviderDescriptor;
import io.cloudbeaver.registry.WebAuthProviderRegistry;
import io.cloudbeaver.server.CBAppConfig;
import io.cloudbeaver.server.CBApplication;
import io.cloudbeaver.server.CBPlatform;
import io.cloudbeaver.service.navigator.WebPropertyFilter;
import io.cloudbeaver.utils.WebAppUtils;
import io.cloudbeaver.utils.WebCommonUtils;
import io.cloudbeaver.utils.WebDataSourceUtils;
Expand All @@ -36,6 +38,7 @@
import org.jkiss.dbeaver.Log;
import org.jkiss.dbeaver.model.DBConstants;
import org.jkiss.dbeaver.model.DBPDataSourceContainer;
import org.jkiss.dbeaver.model.DBPObject;
import org.jkiss.dbeaver.model.access.DBAAuthCredentials;
import org.jkiss.dbeaver.model.app.DBPDataSourceRegistry;
import org.jkiss.dbeaver.model.app.DBPProject;
Expand All @@ -46,6 +49,7 @@
import org.jkiss.dbeaver.model.navigator.DBNModel;
import org.jkiss.dbeaver.model.navigator.DBNProject;
import org.jkiss.dbeaver.model.net.DBWHandlerConfiguration;
import org.jkiss.dbeaver.model.preferences.DBPPropertyDescriptor;
import org.jkiss.dbeaver.model.rm.RMProjectType;
import org.jkiss.dbeaver.registry.DataSourceDescriptor;
import org.jkiss.dbeaver.registry.DataSourceNavigatorSettings;
Expand All @@ -54,6 +58,7 @@
import org.jkiss.dbeaver.registry.driver.DriverDescriptor;
import org.jkiss.dbeaver.registry.network.NetworkHandlerDescriptor;
import org.jkiss.dbeaver.registry.network.NetworkHandlerRegistry;
import org.jkiss.dbeaver.runtime.properties.PropertyCollector;
import org.jkiss.utils.CommonUtils;

import java.io.InputStream;
Expand Down Expand Up @@ -365,4 +370,35 @@ public static Set<String> getApplicableDriversIds() {
.map(DBPDriver::getId)
.collect(Collectors.toSet());
}

/**
* Returns filtered properties collected from object.
*/
@NotNull
public static WebPropertyInfo[] getObjectFilteredProperties(
@NotNull WebSession session,
@NotNull DBPObject object,
@Nullable WebPropertyFilter filter
) {
PropertyCollector propertyCollector = new PropertyCollector(object, true);
propertyCollector.setLocale(session.getLocale());
propertyCollector.collectProperties();
List<WebPropertyInfo> webProps = new ArrayList<>();
for (DBPPropertyDescriptor prop : propertyCollector.getProperties()) {
if (filter != null && !CommonUtils.isEmpty(filter.getIds()) && !filter.getIds().contains(CommonUtils.toString(prop.getId()))) {
continue;
}
WebPropertyInfo webProperty = new WebPropertyInfo(session, prop, propertyCollector);
if (filter != null) {
if (!CommonUtils.isEmpty(filter.getFeatures()) && !webProperty.hasAnyFeature(filter.getFeatures())) {
continue;
}
if (!CommonUtils.isEmpty(filter.getCategories()) && !filter.getCategories().contains(webProperty.getCategory())) {
continue;
}
}
webProps.add(webProperty);
}
return webProps.toArray(new WebPropertyInfo[0]);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,19 +16,17 @@
*/
package io.cloudbeaver.service.navigator;

import io.cloudbeaver.WebServiceUtils;
import io.cloudbeaver.model.WebPropertyInfo;
import io.cloudbeaver.model.session.WebSession;
import org.jkiss.code.Nullable;
import org.jkiss.dbeaver.Log;
import org.jkiss.dbeaver.model.*;
import org.jkiss.dbeaver.model.meta.Property;
import org.jkiss.dbeaver.model.preferences.DBPPropertyDescriptor;
import org.jkiss.dbeaver.model.struct.*;
import org.jkiss.dbeaver.model.struct.rdb.DBSCatalog;
import org.jkiss.dbeaver.model.struct.rdb.DBSSchema;
import org.jkiss.dbeaver.model.struct.rdb.DBSTable;
import org.jkiss.dbeaver.runtime.properties.PropertyCollector;
import org.jkiss.utils.CommonUtils;

import java.util.ArrayList;
import java.util.List;
Expand Down Expand Up @@ -90,26 +88,7 @@ public WebPropertyInfo[] getProperties() {

@Property
public WebPropertyInfo[] filterProperties(@Nullable WebPropertyFilter filter) {
PropertyCollector propertyCollector = new PropertyCollector(object, true);
propertyCollector.setLocale(session.getLocale());
propertyCollector.collectProperties();
List<WebPropertyInfo> webProps = new ArrayList<>();
for (DBPPropertyDescriptor prop : propertyCollector.getProperties()) {
if (filter != null && !CommonUtils.isEmpty(filter.getIds()) && !filter.getIds().contains(CommonUtils.toString(prop.getId()))) {
continue;
}
WebPropertyInfo webProperty = new WebPropertyInfo(session, prop, propertyCollector);
if (filter != null) {
if (!CommonUtils.isEmpty(filter.getFeatures()) && !webProperty.hasAnyFeature(filter.getFeatures())) {
continue;
}
if (!CommonUtils.isEmpty(filter.getCategories()) && !filter.getCategories().contains(webProperty.getCategory())) {
continue;
}
}
webProps.add(webProperty);
}
return webProps.toArray(new WebPropertyInfo[0]);
return WebServiceUtils.getObjectFilteredProperties(session, object, filter);
}

///////////////////////////////////
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,8 +42,8 @@ const equalConfig = {
};

test('Read settings', async () => {
const settings = app.injector.getServiceByClass(AuthSettingsService);
const config = app.injector.getServiceByClass(ServerConfigResource);
const settings = app.serviceProvider.getService(AuthSettingsService);
const config = app.serviceProvider.getService(ServerConfigResource);

server.use(endpoint.query('serverConfig', mockServerConfig(equalConfig)));

Expand Down
11 changes: 5 additions & 6 deletions webapp/packages/core-authentication/src/UserInfoResource.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import { computed, makeObservable, runInAction } from 'mobx';
import { injectable } from '@cloudbeaver/core-di';
import { AutoRunningTask, ISyncExecutor, ITask, SyncExecutor, whileTask } from '@cloudbeaver/core-executor';
import { CachedDataResource, type ResourceKeySimple, ResourceKeyUtils } from '@cloudbeaver/core-resource';
import { SessionDataResource, SessionResource } from '@cloudbeaver/core-root';
import { SessionResource } from '@cloudbeaver/core-root';
import { AuthInfo, AuthLogoutQuery, AuthStatus, GetActiveUserQueryVariables, GraphQLService, UserInfo } from '@cloudbeaver/core-sdk';

import { AUTH_PROVIDER_LOCAL_ID } from './AUTH_PROVIDER_LOCAL_ID';
Expand Down Expand Up @@ -51,8 +51,7 @@ export class UserInfoResource extends CachedDataResource<UserInfo | null, void,
constructor(
private readonly graphQLService: GraphQLService,
private readonly authProviderService: AuthProviderService,
sessionResource: SessionResource,
private readonly sessionDataResource: SessionDataResource,
private readonly sessionResource: SessionResource,
) {
super(() => null, undefined, ['customIncludeOriginDetails', 'includeConfigurationParameters']);

Expand Down Expand Up @@ -111,7 +110,7 @@ export class UserInfoResource extends CachedDataResource<UserInfo | null, void,
if (authInfo.userTokens && authInfo.authStatus === AuthStatus.Success) {
this.resetIncludes();
this.setData(await this.loader());
this.sessionDataResource.markOutdated();
this.sessionResource.markOutdated();
}

return authInfo as AuthInfo;
Expand Down Expand Up @@ -148,7 +147,7 @@ export class UserInfoResource extends CachedDataResource<UserInfo | null, void,
if (authInfo.userTokens && authInfo.authStatus === AuthStatus.Success) {
this.resetIncludes();
this.setData(await this.loader());
this.sessionDataResource.markOutdated();
this.sessionResource.markOutdated();
}

return this.data;
Expand All @@ -167,7 +166,7 @@ export class UserInfoResource extends CachedDataResource<UserInfo | null, void,

this.resetIncludes();
this.setData(await this.loader());
this.sessionDataResource.markOutdated();
this.sessionResource.markOutdated();

return result;
}
Expand Down
21 changes: 21 additions & 0 deletions webapp/packages/core-blocks/src/Table/TableItemGroup.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
/*
* CloudBeaver - Cloud Database Manager
* Copyright (C) 2020-2024 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 { observer } from 'mobx-react-lite';
import { useState } from 'react';

import { TableItemGroupContext } from './TableItemGroupContext';

export interface TableItemGroupProps extends React.PropsWithChildren {
expanded?: boolean;
}

export const TableItemGroup = observer<TableItemGroupProps>(function TableItemGroup({ expanded = true, children }) {
const [internalExpanded, setExpanded] = useState(expanded);

return <TableItemGroupContext.Provider value={{ expanded: internalExpanded, setExpanded }}>{children}</TableItemGroupContext.Provider>;
});
29 changes: 29 additions & 0 deletions webapp/packages/core-blocks/src/Table/TableItemGroupContent.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
/*
* CloudBeaver - Cloud Database Manager
* Copyright (C) 2020-2024 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 { observer } from 'mobx-react-lite';
import { useContext } from 'react';

import { TableItemGroupContext } from './TableItemGroupContext';

export interface TableItemGroupContentProps {
children?: React.ReactNode | (() => React.ReactNode);
}

export const TableItemGroupContent = observer<TableItemGroupContentProps>(function TableItemGroupContent({ children }) {
const context = useContext(TableItemGroupContext);

if (!context) {
throw new Error('TableItemGroupContent can be used only inside TableItemGroup');
}

if (!context.expanded) {
return null;
}

return <>{typeof children === 'function' ? children() : children}</>;
});
14 changes: 14 additions & 0 deletions webapp/packages/core-blocks/src/Table/TableItemGroupContext.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
/*
* CloudBeaver - Cloud Database Manager
* Copyright (C) 2020-2024 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 { createContext } from 'react';

export interface ITableItemGroupContext {
expanded: boolean;
setExpanded: (expanded: boolean) => void;
}
export const TableItemGroupContext = createContext<ITableItemGroupContext | undefined>(undefined);
Loading

0 comments on commit c52a992

Please sign in to comment.