2 * Copyright (C) 2007 EDIT
3 * European Distributed Institute of Taxonomy
4 * http://www.e-taxonomy.eu
6 * The contents of this file are subject to the Mozilla Public License Version 1.1
7 * See LICENSE.TXT at the top of this package for the full license terms.
10 package eu
.etaxonomy
.taxeditor
.store
;
12 import java
.lang
.reflect
.InvocationTargetException
;
13 import java
.lang
.reflect
.Method
;
14 import java
.lang
.reflect
.Type
;
15 import java
.util
.EnumSet
;
17 import org
.eclipse
.core
.runtime
.IProgressMonitor
;
18 import org
.eclipse
.core
.runtime
.jobs
.Job
;
19 import org
.eclipse
.swt
.widgets
.Display
;
20 import org
.springframework
.core
.io
.ClassPathResource
;
21 import org
.springframework
.core
.io
.Resource
;
22 import org
.springframework
.security
.access
.PermissionEvaluator
;
23 import org
.springframework
.security
.authentication
.ProviderManager
;
24 import org
.springframework
.security
.core
.context
.SecurityContext
;
25 import org
.springframework
.security
.core
.context
.SecurityContextHolder
;
27 import eu
.etaxonomy
.cdm
.api
.application
.ICdmApplicationConfiguration
;
28 import eu
.etaxonomy
.cdm
.api
.conversation
.ConversationHolder
;
29 import eu
.etaxonomy
.cdm
.api
.service
.IService
;
30 import eu
.etaxonomy
.cdm
.database
.DbSchemaValidation
;
31 import eu
.etaxonomy
.cdm
.database
.ICdmDataSource
;
32 import eu
.etaxonomy
.cdm
.ext
.geo
.IEditGeoService
;
33 import eu
.etaxonomy
.cdm
.model
.common
.CdmBase
;
34 import eu
.etaxonomy
.cdm
.model
.common
.Language
;
35 import eu
.etaxonomy
.cdm
.persistence
.hibernate
.permission
.CRUD
;
36 import eu
.etaxonomy
.taxeditor
.datasource
.CdmDataSourceRepository
;
37 import eu
.etaxonomy
.taxeditor
.io
.ExportManager
;
38 import eu
.etaxonomy
.taxeditor
.io
.ImportManager
;
39 import eu
.etaxonomy
.taxeditor
.preference
.PreferencesUtil
;
40 import eu
.etaxonomy
.taxeditor
.store
.internal
.TaxeditorStorePlugin
;
41 import eu
.etaxonomy
.taxeditor
.view
.datasource
.CdmDataSourceViewPart
;
44 * This implementation of ICdmDataRepository depends on hibernate sessions to
45 * store the data correctly for the current session. No state is held in this
48 * Only methods that either get or manipulate data are exposed here. So this
49 * class acts as a facade for the methods in cdmlib-service.
55 public class CdmStore
{
57 private static final Resource DEFAULT_APPLICATION_CONTEXT
= new ClassPathResource(
58 "/eu/etaxonomy/cdm/editorApplicationContext.xml",
59 TaxeditorStorePlugin
.class);
60 private static final DbSchemaValidation DEFAULT_DB_SCHEMA_VALIDATION
= DbSchemaValidation
.VALIDATE
;
62 private static CdmStore instance
;
64 private final ICdmApplicationConfiguration applicationConfiguration
;
66 private static ContextManager contextManager
= new ContextManager();
68 private static LoginManager loginManager
= new LoginManager();
70 private static TermManager termManager
= new TermManager();
72 private static SearchManager searchManager
= new SearchManager();
74 private static EditorManager editorManager
= new EditorManager();
76 private static CdmStoreConnector job
;
78 private Language language
;
80 private ICdmDataSource cdmDatasource
;
82 private boolean isConnected
;
89 * @return a {@link eu.etaxonomy.taxeditor.store.CdmStore} object.
91 protected static CdmStore
getDefault() {
92 if (instance
!= null && instance
.isConnected
) {
94 } else if (instance
== null || !instance
.isConnected
) {
98 "Application is not connected to a datastore",
100 "The requested operation is only available when "
101 + "connected to a datasource. You may choose a datasource to connect to or create a new one in the datasource view.");
103 StoreUtil
.showView(CdmDataSourceViewPart
.ID
);
107 throw new RuntimeException();
111 * Initialize the with the last edited datasource
113 public static void connect() {
115 ICdmDataSource datasource
= CdmDataSourceRepository
116 .getCurrentDataSource();
122 * Initialize with a specific datasource
125 * a {@link eu.etaxonomy.cdm.database.ICdmDataSource} object.
127 public static void connect(ICdmDataSource datasource
) {
128 connect(datasource
, DEFAULT_DB_SCHEMA_VALIDATION
,
129 DEFAULT_APPLICATION_CONTEXT
);
133 * Initialize and provide
136 * @param dbSchemaValidation
137 * @param applicationContextBean
139 private static void connect(final ICdmDataSource datasource
,
140 final DbSchemaValidation dbSchemaValidation
,
141 final Resource applicationContextBean
) {
142 StoreUtil
.info("Connecting to datasource: " + datasource
);
144 job
= new CdmStoreConnector(Display
.getDefault(), datasource
,
145 dbSchemaValidation
, applicationContextBean
);
147 job
.setPriority(Job
.BUILD
);
152 public static boolean isConnecting() {
153 return job
!= null && job
.getState() == Job
.RUNNING
;
157 * Closes the current application context
160 * a {@link org.eclipse.core.runtime.IProgressMonitor} object.
162 public static void close(final IProgressMonitor monitor
) {
163 Display
.getDefault().asyncExec(new Runnable() {
167 * @see java.lang.Runnable#run()
171 getContextManager().notifyContextAboutToStop(monitor
);
172 if ((monitor
== null || (!monitor
.isCanceled()) && isActive())) {
173 getContextManager().notifyContextStop(monitor
);
180 private void close() {
182 cdmDatasource
= null;
185 static void setInstance(ICdmApplicationConfiguration applicationController
,
186 ICdmDataSource dataSource
) {
187 instance
= new CdmStore(applicationController
, dataSource
);
190 private CdmStore(ICdmApplicationConfiguration applicationController
,
191 ICdmDataSource dataSource
) {
192 this.applicationConfiguration
= applicationController
;
193 this.cdmDatasource
= dataSource
;
198 * All calls to the datastore require
202 private ICdmApplicationConfiguration
getApplicationConfiguration() {
204 return applicationConfiguration
;
205 } catch (Exception e
) {
206 StoreUtil
.error(CdmStore
.class, e
);
213 * getCurrentApplicationController
217 * {@link eu.etaxonomy.cdm.remote.api.application.CdmApplicationController}
220 public static ICdmApplicationConfiguration
getCurrentApplicationConfiguration() {
221 if (getDefault() != null) {
222 return getDefault().getApplicationConfiguration();
232 * Creates a new conversation, binds resources to the conversation and start
233 * a transaction for this conversation.
235 * @return a {@link eu.etaxonomy.cdm.api.conversation.ConversationHolder}
238 public static ConversationHolder
createConversation() {
239 ConversationHolder conversation
= getCurrentApplicationConfiguration()
242 conversation
.startTransaction();
244 StoreUtil
.errorDialog("No database connection", CdmStore
.class, "No database connection available", e
);
250 * Generic method that will scan the getters of {@link ICdmApplicationConfiguration} for the given service
251 * interface. If a matching getter is found the according service implementation is returned by
252 * invoking the getter otherwise the method returns <code>null</code>.
255 * @param serviceClass
256 * @return the configured implementation of <code>serviceClass</code> or <code>null</code>
258 public static <T
extends IService
> T
getService(Class
<T
> serviceClass
) {
259 ICdmApplicationConfiguration configuration
= getCurrentApplicationConfiguration();
261 Method
[] methods
= ICdmApplicationConfiguration
.class.getDeclaredMethods();
265 for (Method method
: methods
) {
266 Type type
= method
.getGenericReturnType();
268 if (type
.equals(serviceClass
)) {
270 service
= (T
) method
.invoke(configuration
, null);
272 } catch (IllegalArgumentException e
) {
273 StoreUtil
.error(CdmStore
.class, e
);
274 } catch (IllegalAccessException e
) {
275 StoreUtil
.error(CdmStore
.class, e
);
276 } catch (InvocationTargetException e
) {
277 StoreUtil
.error(CdmStore
.class, e
);
287 * getAuthenticationManager
291 * {@link org.springframework.security.authentication.ProviderManager}
294 public static ProviderManager
getAuthenticationManager() {
295 return getCurrentApplicationConfiguration().getAuthenticationManager();
300 * getAuthenticationManager
304 * {@link PermissionEvaluator} object.
306 public static PermissionEvaluator
getPermissionEvaluator() {
307 return getCurrentApplicationConfiguration().getPermissionEvaluator();
315 * @return a {@link eu.etaxonomy.cdm.ext.geo.IEditGeoService} object.
317 public static IEditGeoService
getGeoService() {
318 return (IEditGeoService
) getCurrentApplicationConfiguration().getBean(
323 * SECURITY RELATED CONVENIENCE METHODS
327 * @see org.springframework.security.access.PermissionEvaluator#hasPermission(org.springframework.security.core.Authentication, java.lang.Object, java.lang.Object)
329 * @param targetDomainObject
333 public static boolean currentAuthentiationHasPermission(CdmBase targetDomainObject
, EnumSet
<CRUD
> permission
){
334 //TODO use getCurrentApplicationConfiguration().currentAuthentiationHasPermission(CdmBase targetDomainObject, Operation permission) instead
335 SecurityContext context
= SecurityContextHolder
.getContext();
336 PermissionEvaluator pe
= getPermissionEvaluator();
337 return getPermissionEvaluator().hasPermission(context
.getAuthentication(), targetDomainObject
, permission
);
341 * @see org.springframework.security.access.PermissionEvaluator#hasPermission(org.springframework.security.core.Authentication, java.lang.Object, java.lang.Object)
343 * @param targetDomainObject
347 public static boolean currentAuthentiationHasPermission(Class
<?
extends CdmBase
> targetType
, EnumSet
<CRUD
> permission
){
348 SecurityContext context
= SecurityContextHolder
.getContext();
349 return getPermissionEvaluator().hasPermission(context
.getAuthentication(), null, targetType
.getName(), permission
);
361 * @return a {@link eu.etaxonomy.cdm.model.common.Language} object.
363 public static Language
getDefaultLanguage() {
364 if (getDefault().getLanguage() == null) {
365 getDefault().setLanguage(PreferencesUtil
.getGlobalLanguage());
367 return getDefault().getLanguage();
376 * a {@link eu.etaxonomy.cdm.model.common.Language} object.
378 public static void setDefaultLanguage(Language language
) {
379 getDefault().setLanguage(language
);
383 * @return the language
385 private Language
getLanguage() {
391 * the language to set
393 private void setLanguage(Language language
) {
394 this.language
= language
;
403 * Getter for the field <code>loginManager</code>.
406 * @return a {@link eu.etaxonomy.taxeditor.store.LoginManager} object.
408 public static LoginManager
getLoginManager() {
414 * Getter for the field <code>contextManager</code>.
417 * @return a {@link eu.etaxonomy.taxeditor.store.ContextManager} object.
419 public static ContextManager
getContextManager() {
420 return contextManager
;
423 public static TermManager
getTermManager() {
427 public static SearchManager
getSearchManager() {
428 return searchManager
;
431 public static EditorManager
getEditorManager() {
432 return editorManager
;
436 * IMPORT/EXPORT FACTORIES
441 * Getter for the field <code>importHandler</code>.
444 * @return a {@link eu.etaxonomy.taxeditor.io.ImportManager} object.
446 public static ImportManager
getImportManager() {
447 return ImportManager
.NewInstance(getCurrentApplicationConfiguration());
452 * Getter for the field <code>exportHandler</code>.
455 * @return a {@link eu.etaxonomy.taxeditor.io.ExportManager} object.
457 public static ExportManager
getExportManager() {
458 return ExportManager
.NewInstance(getCurrentApplicationConfiguration());
462 * Whether this CdmStore is currently connected to a datasource
466 public static boolean isActive() {
467 return instance
!= null && instance
.isConnected
;
475 * @return a {@link eu.etaxonomy.cdm.database.ICdmDataSource} object.
477 public static ICdmDataSource
getDataSource() {
479 return instance
.getDatasource();
487 private ICdmDataSource
getDatasource() {
488 return cdmDatasource
;