From c8d10e187dc9ffc00b00c05ada1f39f5e4d56c49 Mon Sep 17 00:00:00 2001 From: serge-rider Date: Mon, 4 May 2020 20:34:02 +0300 Subject: [PATCH] Core service refactoring (auth) --- .../schema/service.core.graphqls | 4 + .../io/cloudbeaver/model/WebServerConfig.java | 65 +++++-------- .../cloudbeaver/model/session/WebSession.java | 11 --- .../io/cloudbeaver/server/CBAppConfig.java | 20 ++++ .../src/io/cloudbeaver/server/CBPlatform.java | 24 ----- .../service/core/DBWServiceCore.java | 43 +++++++++ .../service/core/WebServiceBindingCore.java | 31 +++--- .../service/core/impl/WebServiceCore.java | 95 +++++++++++++++++++ 8 files changed, 200 insertions(+), 93 deletions(-) diff --git a/server/bundles/io.cloudbeaver.server/schema/service.core.graphqls b/server/bundles/io.cloudbeaver.server/schema/service.core.graphqls index 5d28832088..8f89744841 100644 --- a/server/bundles/io.cloudbeaver.server/schema/service.core.graphqls +++ b/server/bundles/io.cloudbeaver.server/schema/service.core.graphqls @@ -51,11 +51,15 @@ type WebServiceConfig { type ServerConfig { name: String! version: String! + + anonymousAccessEnabled: Boolean + authenticationEnabled: Boolean supportsPredefinedConnections: Boolean supportsProvidedConnections: Boolean supportsCustomConnections: Boolean supportsConnectionBrowser: Boolean supportsWorkspaces: Boolean + supportedLanguages: [ ServerLanguage ]! services: [ WebServiceConfig ] productConfiguration: Object! diff --git a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/WebServerConfig.java b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/WebServerConfig.java index bc649cae28..62a39d9ec5 100644 --- a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/WebServerConfig.java +++ b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/WebServerConfig.java @@ -16,13 +16,14 @@ */ package io.cloudbeaver.model; -import io.cloudbeaver.WebAction; -import io.cloudbeaver.server.CBPlatform; import io.cloudbeaver.registry.WebServiceDescriptor; import io.cloudbeaver.registry.WebServiceRegistry; +import io.cloudbeaver.server.CBApplication; +import io.cloudbeaver.server.CBPlatform; import org.jkiss.dbeaver.model.meta.Property; import org.jkiss.dbeaver.registry.language.PlatformLanguageDescriptor; import org.jkiss.dbeaver.registry.language.PlatformLanguageRegistry; +import org.jkiss.dbeaver.utils.GeneralUtils; import java.util.ArrayList; import java.util.List; @@ -33,73 +34,53 @@ import java.util.Map; */ public class WebServerConfig { - private String name; - private String version; - private boolean supportsPredefinedConnections; - private boolean supportsCustomConnections; - private boolean supportsConnectionBrowser; - private boolean supportsWorkspaces; + private final CBApplication application; - public WebServerConfig(String name, String version) { - this.name = name; - this.version = version; + public WebServerConfig(CBApplication application) { + this.application = application; } @Property public String getName() { - return name; - } - - public void setName(String name) { - this.name = name; + return application.getServerName(); } @Property public String getVersion() { - return version; + return GeneralUtils.getProductVersion().toString(); } - public void setVersion(String version) { - this.version = version; + @Property + public boolean isAnonymousAccessEnabled() { + return application.getAppConfiguration().isAnonymousAccessEnabled(); + } + + @Property + public boolean isAuthenticationEnabled() { + return application.getAppConfiguration().isAuthenticationEnabled(); } @Property public boolean isSupportsPredefinedConnections() { - return supportsPredefinedConnections; - } - - public void setSupportsPredefinedConnections(boolean supportsPredefinedConnections) { - this.supportsPredefinedConnections = supportsPredefinedConnections; + return application.getAppConfiguration().isSupportsPredefinedConnections(); } @Property public boolean isSupportsCustomConnections() { - return supportsCustomConnections; - } - - public void setSupportsCustomConnections(boolean supportsCustomConnections) { - this.supportsCustomConnections = supportsCustomConnections; + return application.getAppConfiguration().isSupportsCustomConnections(); } @Property public boolean isSupportsConnectionBrowser() { - return supportsConnectionBrowser; - } - - public void setSupportsConnectionBrowser(boolean supportsConnectionBrowser) { - this.supportsConnectionBrowser = supportsConnectionBrowser; + return application.getAppConfiguration().isSupportsConnectionBrowser(); } @Property public boolean isSupportsWorkspaces() { - return supportsWorkspaces; + return application.getAppConfiguration().isSupportsUserWorkspaces(); } - public void setSupportsWorkspaces(boolean supportsWorkspaces) { - this.supportsWorkspaces = supportsWorkspaces; - } - - @WebAction + @Property public WebServerLanguage[] getSupportedLanguages() { List langs = PlatformLanguageRegistry.getInstance().getLanguages(); WebServerLanguage[] webLangs = new WebServerLanguage[langs.size()]; @@ -109,7 +90,7 @@ public class WebServerConfig { return webLangs; } - @WebAction + @Property public WebServiceConfig[] getServices() { List services = new ArrayList<>(); for (WebServiceDescriptor wsd : WebServiceRegistry.getInstance().getWebServices()) { @@ -118,7 +99,7 @@ public class WebServerConfig { return services.toArray(new WebServiceConfig[0]); } - @WebAction + @Property public Map getProductConfiguration() { return CBPlatform.getInstance().getApplication().getProductConfiguration(); } diff --git a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/session/WebSession.java b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/session/WebSession.java index 17847f3c06..81f6c9943e 100644 --- a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/session/WebSession.java +++ b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/model/session/WebSession.java @@ -439,17 +439,6 @@ public class WebSession { return progressMonitor; } - public List getDriverList(@Nullable String driverId) { - List result = new ArrayList<>(); - for (DBPDriver driver : CBPlatform.getInstance().getApplicableDrivers()) { - if (driverId == null || driverId.equals(WebServiceUtils.makeDriverFullId(driver))) { - result.add(new WebDatabaseDriverConfig(this, driver)); - } - } - - return result; - } - /////////////////////////////////////////////////////// // Async model diff --git a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBAppConfig.java b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBAppConfig.java index 471f39d1ca..fdb5424395 100644 --- a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBAppConfig.java +++ b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBAppConfig.java @@ -24,6 +24,10 @@ public class CBAppConfig { private boolean authenticationEnabled = true; private String anonymousUserRole = CBConstants.DEFAUL_APP_ANONYMOUS_ROLE_NAME; private String defaultUserRole = CBConstants.DEFAUL_APP_ANONYMOUS_ROLE_NAME; + private boolean supportsPredefinedConnections = true; + private boolean supportsCustomConnections = true; + private boolean supportsConnectionBrowser = false; + private boolean supportsUserWorkspaces = false; public boolean isAuthenticationEnabled() { return authenticationEnabled; @@ -40,4 +44,20 @@ public class CBAppConfig { public String getDefaultUserRole() { return defaultUserRole; } + + public boolean isSupportsPredefinedConnections() { + return supportsPredefinedConnections; + } + + public boolean isSupportsCustomConnections() { + return supportsCustomConnections; + } + + public boolean isSupportsConnectionBrowser() { + return supportsConnectionBrowser; + } + + public boolean isSupportsUserWorkspaces() { + return supportsUserWorkspaces; + } } diff --git a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBPlatform.java b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBPlatform.java index 9b274fb5ee..5ad3670a1d 100644 --- a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBPlatform.java +++ b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/server/CBPlatform.java @@ -306,32 +306,8 @@ public class CBPlatform extends BasePlatformImpl { return false; } - public WebServerConfig getServerConfig() { - WebServerConfig config = new WebServerConfig( - CBApplication.getInstance().getServerName(), - GeneralUtils.getProductVersion().toString() - ); - config.setSupportsPredefinedConnections(true); - return config; - } - public WebSessionManager getSessionManager() { return sessionManager; } - public List getGlobalDataSources() throws DBWebException { - List result = new ArrayList<>(); - DBPDataSourceRegistry dsRegistry = WebServiceUtils.getDataSourceRegistry(); - - for (DBPDataSourceContainer ds : dsRegistry.getDataSources()) { - if (applicableDrivers.contains(ds.getDriver()) && !ds.isProvided()) { - result.add(new WebDataSourceConfig(ds)); - } else { - log.debug("Global datasource '" + ds.getName() + "' ignored - driver is not applicable"); - } - } - - return result; - } - } diff --git a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/DBWServiceCore.java b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/DBWServiceCore.java index e7838c87bd..0ecf9e4862 100644 --- a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/DBWServiceCore.java +++ b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/DBWServiceCore.java @@ -17,10 +17,53 @@ package io.cloudbeaver.service.core; import io.cloudbeaver.DBWService; +import io.cloudbeaver.DBWebException; +import io.cloudbeaver.WebAction; +import io.cloudbeaver.model.WebDataSourceConfig; +import io.cloudbeaver.model.WebDatabaseDriverConfig; +import io.cloudbeaver.model.WebServerConfig; +import io.cloudbeaver.model.WebServerMessage; +import io.cloudbeaver.model.session.WebSession; +import org.jkiss.dbeaver.model.exec.DBCException; + +import javax.servlet.http.HttpServletRequest; +import java.util.List; +import java.util.Set; /** * Web service API */ public interface DBWServiceCore extends DBWService { + @WebAction(requirePermissions = {}) + WebServerConfig getServerConfig() throws DBWebException; + + @WebAction + List getDriverList(WebSession webSession, String driverId) throws DBWebException; + + @WebAction + List getGlobalDataSources() throws DBWebException; + + @WebAction + String[] getSessionPermissions(WebSession webSession) throws DBWebException; + + /////////////////////////////////////////// + // Session + + @WebAction(requirePermissions = {}) + WebSession openSession(WebSession webSession) throws DBWebException; + + @WebAction + WebSession getSessionState(WebSession webSession) throws DBWebException; + + @WebAction + List readSessionLog(WebSession webSession, Integer maxEntries, Boolean clearEntries) throws DBWebException; + + @WebAction + boolean closeSession(HttpServletRequest request) throws DBWebException; + + @WebAction + boolean touchSession(HttpServletRequest request) throws DBWebException; + + boolean changeSessionLanguage(WebSession webSession, String locale); } diff --git a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/WebServiceBindingCore.java b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/WebServiceBindingCore.java index 352ffd5fc0..c7d9a02c53 100644 --- a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/WebServiceBindingCore.java +++ b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/WebServiceBindingCore.java @@ -16,9 +16,12 @@ */ package io.cloudbeaver.service.core; +import graphql.TypeResolutionEnvironment; import graphql.schema.idl.TypeRuntimeWiring; import io.cloudbeaver.DBWebException; +import io.cloudbeaver.model.WebServerConfig; import io.cloudbeaver.model.session.WebSessionManager; +import io.cloudbeaver.server.CBApplication; import io.cloudbeaver.server.CBPlatform; import io.cloudbeaver.server.graphql.GraphQLEndpoint; import io.cloudbeaver.service.DBWBindingContext; @@ -39,27 +42,25 @@ public class WebServiceBindingCore extends WebServiceBindingBase CBPlatform platform = CBPlatform.getInstance(); WebSessionManager sessionManager = platform.getSessionManager(); model.getQueryType() - .dataFetcher("serverConfig", env -> platform.getServerConfig()) + .dataFetcher("serverConfig", env -> getService(env).getServerConfig()) - .dataFetcher("driverList", env -> sessionManager.getWebSession(GraphQLEndpoint.getServletRequest(env)).getDriverList(env.getArgument("id"))) - .dataFetcher("dataSourceList", env -> platform.getGlobalDataSources()) + .dataFetcher("driverList", env -> getService(env).getDriverList(getWebSession(env), env.getArgument("id"))) + .dataFetcher("dataSourceList", env -> getService(env).getGlobalDataSources()) - .dataFetcher("sessionPermissions", env -> sessionManager.getWebSession(GraphQLEndpoint.getServletRequest(env)).getSessionPermissions()) - .dataFetcher("sessionState", env -> sessionManager.getWebSession(GraphQLEndpoint.getServletRequest(env))) + .dataFetcher("sessionPermissions", env -> getService(env).getSessionPermissions(getWebSession(env))) + .dataFetcher("sessionState", env -> getService(env).getSessionState(getWebSession(env))) - .dataFetcher("readSessionLog", env -> sessionManager.getWebSession(GraphQLEndpoint.getServletRequest(env), false, true).readLog( + .dataFetcher("readSessionLog", env -> getService(env).readSessionLog( + getWebSession(env), env.getArgument("maxEntries"), env.getArgument("clearEntries"))) ; model.getMutationType() - .dataFetcher("openSession", env -> sessionManager.getWebSession(GraphQLEndpoint.getServletRequest(env), false)) - .dataFetcher("closeSession", env -> sessionManager.closeSession(GraphQLEndpoint.getServletRequest(env))) - .dataFetcher("touchSession", env -> sessionManager.touchSession(GraphQLEndpoint.getServletRequest(env))) - .dataFetcher("changeSessionLanguage", env -> { - sessionManager.getWebSession(GraphQLEndpoint.getServletRequest(env)).setLocale(env.getArgument("locale")); - return true; - }) + .dataFetcher("openSession", env -> getService(env).openSession(sessionManager.getWebSession(GraphQLEndpoint.getServletRequest(env), false))) + .dataFetcher("closeSession", env -> getService(env).closeSession(GraphQLEndpoint.getServletRequest(env))) + .dataFetcher("touchSession", env -> getService(env).touchSession(GraphQLEndpoint.getServletRequest(env))) + .dataFetcher("changeSessionLanguage", env -> getService(env).changeSessionLanguage(getWebSession(env), env.getArgument("locale"))) .dataFetcher("openConnection", env -> sessionManager.openConnection(GraphQLEndpoint.getServletRequest(env), env.getArgument("config"))) .dataFetcher("createConnection", env -> sessionManager.createConnection(GraphQLEndpoint.getServletRequest(env), env.getArgument("config"))) @@ -76,9 +77,7 @@ public class WebServiceBindingCore extends WebServiceBindingBase ) ; - model.getRuntimeWiring().type(TypeRuntimeWiring.newTypeWiring("AsyncTaskResult").typeResolver(env -> { - return env.getObject(); - }) + model.getRuntimeWiring().type(TypeRuntimeWiring.newTypeWiring("AsyncTaskResult").typeResolver(TypeResolutionEnvironment::getObject) ); } diff --git a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/impl/WebServiceCore.java b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/impl/WebServiceCore.java index ca74ceb073..05ea8010b5 100644 --- a/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/impl/WebServiceCore.java +++ b/server/bundles/io.cloudbeaver.server/src/io/cloudbeaver/service/core/impl/WebServiceCore.java @@ -17,10 +17,105 @@ package io.cloudbeaver.service.core.impl; +import io.cloudbeaver.DBWebException; +import io.cloudbeaver.WebServiceUtils; +import io.cloudbeaver.model.WebDataSourceConfig; +import io.cloudbeaver.model.WebDatabaseDriverConfig; +import io.cloudbeaver.model.WebServerConfig; +import io.cloudbeaver.model.WebServerMessage; +import io.cloudbeaver.model.session.WebSession; +import io.cloudbeaver.server.CBApplication; +import io.cloudbeaver.server.CBPlatform; +import io.cloudbeaver.server.graphql.GraphQLEndpoint; import io.cloudbeaver.service.core.DBWServiceCore; +import org.jkiss.dbeaver.Log; +import org.jkiss.dbeaver.model.DBPDataSourceContainer; +import org.jkiss.dbeaver.model.app.DBPDataSourceRegistry; +import org.jkiss.dbeaver.model.connection.DBPDriver; +import org.jkiss.dbeaver.model.exec.DBCException; + +import javax.servlet.http.HttpServletRequest; +import java.util.ArrayList; +import java.util.List; /** * Web service implementation */ public class WebServiceCore implements DBWServiceCore { + + private static final Log log = Log.getLog(WebServiceCore.class); + + @Override + public WebServerConfig getServerConfig() { + return new WebServerConfig(CBApplication.getInstance()); + } + + @Override + public List getDriverList(WebSession webSession, String driverId) { + List result = new ArrayList<>(); + for (DBPDriver driver : CBPlatform.getInstance().getApplicableDrivers()) { + if (driverId == null || driverId.equals(WebServiceUtils.makeDriverFullId(driver))) { + result.add(new WebDatabaseDriverConfig(webSession, driver)); + } + } + return result; + } + + @Override + public List getGlobalDataSources() throws DBWebException { + + List result = new ArrayList<>(); + DBPDataSourceRegistry dsRegistry = WebServiceUtils.getDataSourceRegistry(); + + for (DBPDataSourceContainer ds : dsRegistry.getDataSources()) { + if (CBPlatform.getInstance().getApplicableDrivers().contains(ds.getDriver()) && !ds.isProvided()) { + result.add(new WebDataSourceConfig(ds)); + } else { + log.debug("Global datasource '" + ds.getName() + "' ignored - driver is not applicable"); + } + } + + return result; + } + + @Override + public String[] getSessionPermissions(WebSession webSession) throws DBWebException { + try { + return webSession.getSessionPermissions().toArray(new String[0]); + } catch (DBCException e) { + throw new DBWebException("Error reading session permissions", e); + } + } + + @Override + public WebSession openSession(WebSession webSession) { + return webSession; + } + + @Override + public WebSession getSessionState(WebSession webSession) { + return webSession; + } + + @Override + public List readSessionLog(WebSession webSession, Integer maxEntries, Boolean clearEntries) { + return webSession.readLog(maxEntries, clearEntries); + } + + @Override + public boolean closeSession(HttpServletRequest request) { + return CBPlatform.getInstance().getSessionManager().closeSession(request); + } + + @Override + public boolean touchSession(HttpServletRequest request) throws DBWebException { + return CBPlatform.getInstance().getSessionManager().touchSession(request); + } + + @Override + public boolean changeSessionLanguage(WebSession webSession, String locale) { + webSession.setLocale(locale); + return true; + } + }