had to rename the packages to make them compliant with buckminster
[taxeditor.git] / eu.etaxonomy.taxeditor.store / src / main / java / eu / etaxonomy / taxeditor / store / CdmStore.java
1 /**
2 * Copyright (C) 2007 EDIT
3 * European Distributed Institute of Taxonomy
4 * http://www.e-taxonomy.eu
5 *
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.
8 */
9
10 package eu.etaxonomy.taxeditor.store;
11
12 import java.lang.reflect.InvocationTargetException;
13 import java.lang.reflect.Method;
14 import java.lang.reflect.Type;
15
16 import org.eclipse.core.runtime.IProgressMonitor;
17 import org.eclipse.core.runtime.jobs.Job;
18 import org.eclipse.swt.widgets.Display;
19 import org.springframework.core.io.ClassPathResource;
20 import org.springframework.core.io.Resource;
21 import org.springframework.security.authentication.ProviderManager;
22
23 import eu.etaxonomy.cdm.api.application.CdmApplicationController;
24 import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
25 import eu.etaxonomy.cdm.api.conversation.ConversationHolder;
26 import eu.etaxonomy.cdm.api.service.IService;
27 import eu.etaxonomy.cdm.database.DbSchemaValidation;
28 import eu.etaxonomy.cdm.database.ICdmDataSource;
29 import eu.etaxonomy.cdm.ext.geo.IEditGeoService;
30 import eu.etaxonomy.cdm.model.common.Language;
31 import eu.etaxonomy.taxeditor.datasource.CdmDataSourceRepository;
32 import eu.etaxonomy.taxeditor.io.ExportManager;
33 import eu.etaxonomy.taxeditor.io.ImportManager;
34 import eu.etaxonomy.taxeditor.preference.PreferencesUtil;
35 import eu.etaxonomy.taxeditor.store.internal.TaxeditorStorePlugin;
36 import eu.etaxonomy.taxeditor.view.datasource.CdmDataSourceViewPart;
37
38 /**
39 * This implementation of ICdmDataRepository depends on hibernate sessions to store the data correctly
40 * for the current session. No state is held in this class.
41 *
42 * Only methods that either get or manipulate data are exposed here. So this class acts as a facade
43 * for the methods in cdmlib-service.
44 *
45 * @author n.hoffmann
46 * @created 17.03.2009
47 * @version 1.0
48 */
49 public class CdmStore{
50
51 private static final Resource DEFAULT_APPLICATION_CONTEXT = new ClassPathResource("/eu/etaxonomy/cdm/editorApplicationContext.xml", TaxeditorStorePlugin.class);
52 private static final DbSchemaValidation DEFAULT_DB_SCHEMA_VALIDATION = DbSchemaValidation.VALIDATE;
53
54 private static CdmStore instance;
55
56 private CdmApplicationController applicationController;
57
58 private static LoginManager loginManager;
59
60 private static ImportManager importManager;
61
62 private static ExportManager exportManager;
63
64 private static ContextManager contextManager;
65
66 private static TermManager termManager = new TermManager();
67
68 private static SearchManager searchManager;
69
70 private static EditorManager editorManager;
71
72 private static CdmStoreConnector job;
73
74 private Language language;
75
76 private ICdmDataSource cdmDatasource;
77
78 private boolean isConnected;
79
80 /**
81 * <p>getDefault</p>
82 *
83 * @return a {@link eu.etaxonomy.taxeditor.store.CdmStore} object.
84 */
85 protected static CdmStore getDefault(){
86 if(instance != null && instance.isConnected){
87 return instance;
88 }else if(instance == null || !instance.isConnected){
89
90 StoreUtil.warningDialog("Application is not connected to a datastore", instance, "The requested operation is only available when " +
91 "connected to a datasource. You may choose a datasource to connect to or create a new one in the datasource view.");
92
93 StoreUtil.showView(CdmDataSourceViewPart.ID);
94
95 }
96
97 throw new RuntimeException();
98 }
99
100 /**
101 * Initialize the with the last edited datasource
102 */
103 public static void connect() {
104
105 ICdmDataSource datasource = CdmDataSourceRepository.getCurrentDataSource();
106
107 connect(datasource);
108 }
109
110 /**
111 * Initialize with a specific datasource
112 *
113 * @param datasource a {@link eu.etaxonomy.cdm.database.ICdmDataSource} object.
114 */
115 public static void connect(ICdmDataSource datasource) {
116 connect(datasource, DEFAULT_DB_SCHEMA_VALIDATION, DEFAULT_APPLICATION_CONTEXT);
117 }
118
119 /**
120 * Initialize and provide
121 *
122 * @param datasource
123 * @param dbSchemaValidation
124 * @param applicationContextBean
125 */
126 private static void connect(final ICdmDataSource datasource, final DbSchemaValidation dbSchemaValidation, final Resource applicationContextBean){
127 StoreUtil.info("Connecting to datasource: " + datasource);
128
129 job = new CdmStoreConnector(Display.getDefault(), datasource, dbSchemaValidation, applicationContextBean);
130 job.setUser(true);
131 job.setPriority(Job.BUILD);
132 job.schedule();
133
134 }
135
136 public static boolean isConnecting(){
137 return job != null && job.getState() == Job.RUNNING;
138 }
139
140 /**
141 * Closes the current application context
142 *
143 * @param monitor a {@link org.eclipse.core.runtime.IProgressMonitor} object.
144 */
145 public static void close(final IProgressMonitor monitor){
146 Display.getDefault().asyncExec(new Runnable(){
147 /* (non-Javadoc)
148 * @see java.lang.Runnable#run()
149 */
150 @Override
151 public void run() {
152 getContextManager().notifyContextAboutToStop(monitor);
153 if((monitor == null || (!monitor.isCanceled()) && isActive())){
154 getContextManager().notifyContextStop(monitor);
155 if(instance.getApplicationController() != null){
156 instance.getApplicationController().close();
157 }
158 instance.close();
159 }
160 }
161 });
162 }
163
164 private void close() {
165 isConnected = false;
166 cdmDatasource = null;
167 }
168
169 static void setInstance(CdmApplicationController applicationController, ICdmDataSource dataSource){
170 instance = new CdmStore(applicationController, dataSource);
171 }
172
173 private CdmStore(CdmApplicationController applicationController, ICdmDataSource dataSource){
174 this.applicationController = applicationController;
175 this.cdmDatasource = dataSource;
176 isConnected = true;
177 }
178
179 /**
180 * All calls to the datastore require
181 *
182 * @return
183 */
184 private CdmApplicationController getApplicationController(){
185 try{
186 return applicationController;
187 }catch(Exception e){
188 StoreUtil.error(CdmStore.class, e);
189 }
190 return null;
191 }
192
193 /**
194 * <p>getCurrentApplicationController</p>
195 *
196 * @return a {@link eu.etaxonomy.cdm.api.application.CdmApplicationController} object.
197 */
198 public static CdmApplicationController getCurrentApplicationController(){
199 if(getDefault() != null){
200 return getDefault().getApplicationController();
201 }
202 return null;
203 }
204
205 /*
206 * CONVERSATIONS
207 */
208
209 /**
210 * Creates a new conversation, binds resources to the conversation and
211 * start a transaction for this conversation.
212 *
213 * @return a {@link eu.etaxonomy.cdm.api.conversation.ConversationHolder} object.
214 */
215 public static ConversationHolder createConversation() {
216 ConversationHolder conversation = getCurrentApplicationController().NewConversation();
217
218 conversation.startTransaction();
219 return conversation;
220 }
221
222 /**
223 * Generic method that will return an implementation of the given service interface
224 * or <code>null</code> if the
225 *
226 * @param <T>
227 * @param serviceClass
228 * @return
229 */
230 public static <T extends IService> T getService(Class<T> serviceClass){
231 ICdmApplicationConfiguration controller = getCurrentApplicationController();
232
233 Method[] methods = ICdmApplicationConfiguration.class.getDeclaredMethods();
234
235 T service = null;
236
237 for(Method method : methods){
238 Type type = method.getGenericReturnType();
239
240 if(type.equals(serviceClass)){
241 try {
242 service = (T) method.invoke(controller, null);
243 break;
244 } catch (IllegalArgumentException e) {
245 StoreUtil.error(CdmStore.class, e);
246 } catch (IllegalAccessException e) {
247 StoreUtil.error(CdmStore.class, e);
248 } catch (InvocationTargetException e) {
249 StoreUtil.error(CdmStore.class, e);
250 }
251 }
252 }
253
254 return service;
255 }
256
257 /**
258 * <p>getAuthenticationManager</p>
259 *
260 * @return a {@link org.springframework.security.authentication.ProviderManager} object.
261 */
262 public static ProviderManager getAuthenticationManager() { return getCurrentApplicationController().getAuthenticationManager();}
263
264 /**
265 * <p>getGeoService</p>
266 *
267 * @return a {@link eu.etaxonomy.cdm.ext.geo.IEditGeoService} object.
268 */
269 public static IEditGeoService getGeoService(){
270 return (IEditGeoService) getCurrentApplicationController().getBean("editGeoService");
271 }
272
273 /*
274 * LANGUAGE
275 */
276
277 /**
278 * <p>getDefaultLanguage</p>
279 *
280 * @return a {@link eu.etaxonomy.cdm.model.common.Language} object.
281 */
282 public static Language getDefaultLanguage(){
283 if(getDefault().getLanguage() == null){
284 getDefault().setLanguage(PreferencesUtil.getGlobalLanguage());
285 }
286 return getDefault().getLanguage();
287 }
288
289 /**
290 * <p>setDefaultLanguage</p>
291 *
292 * @param language a {@link eu.etaxonomy.cdm.model.common.Language} object.
293 */
294 public static void setDefaultLanguage(Language language){
295 getDefault().setLanguage(language);
296 }
297
298 /**
299 * @return the language
300 */
301 private Language getLanguage() {
302 return language;
303 }
304
305 /**
306 * @param language the language to set
307 */
308 private void setLanguage(Language language) {
309 this.language = language;
310 }
311
312 /*
313 * LOGIN
314 */
315
316 /**
317 * <p>Getter for the field <code>loginManager</code>.</p>
318 *
319 * @return a {@link eu.etaxonomy.taxeditor.store.LoginManager} object.
320 */
321 public static LoginManager getLoginManager(){
322 if(loginManager == null){
323 loginManager = new LoginManager();
324 }
325 return loginManager;
326 }
327
328 /**
329 * <p>Getter for the field <code>contextManager</code>.</p>
330 *
331 * @return a {@link eu.etaxonomy.taxeditor.store.ContextManager} object.
332 */
333 public static ContextManager getContextManager(){
334 if(contextManager == null){
335 contextManager = new ContextManager();
336 }
337 return contextManager;
338 }
339
340 public static TermManager getTermManager(){
341 return termManager;
342 }
343
344 public static SearchManager getSearchManager(){
345 if(searchManager == null){
346 searchManager = new SearchManager();
347 }
348 return searchManager;
349 }
350
351 public static EditorManager getEditorManager() {
352 if(editorManager == null){
353 editorManager = new EditorManager();
354 }
355
356 return editorManager;
357 }
358
359 /*
360 * IMPORT/EXPORT FACTORIES
361 */
362
363 /**
364 * <p>Getter for the field <code>importHandler</code>.</p>
365 *
366 * @return a {@link eu.etaxonomy.taxeditor.io.ImportManager} object.
367 */
368 public static ImportManager getImportManager(){
369 if(importManager == null){
370 importManager = ImportManager.NewInstance(getCurrentApplicationController());
371 }
372 return importManager;
373 }
374
375 /**
376 * <p>Getter for the field <code>exportHandler</code>.</p>
377 *
378 * @return a {@link eu.etaxonomy.taxeditor.io.ExportManager} object.
379 */
380 public static ExportManager getExportManager(){
381 if(exportManager == null){
382 exportManager = ExportManager.NewInstance(getCurrentApplicationController());
383 }
384 return exportManager;
385 }
386
387 /**
388 * Whether this CdmStore is currently connected to a datasource
389 *
390 * @return a boolean.
391 */
392 public static boolean isActive(){
393 return instance != null && instance.isConnected;
394 }
395
396 /**
397 * <p>getDataSource</p>
398 *
399 * @return a {@link eu.etaxonomy.cdm.database.ICdmDataSource} object.
400 */
401 public static ICdmDataSource getDataSource(){
402 if(isActive()){
403 return instance.getDatasource();
404 }
405 return null;
406 }
407
408 /**
409 * @return
410 */
411 private ICdmDataSource getDatasource() {
412 return cdmDatasource;
413 }
414
415 }