preliminary fix for ICBN bug #3658
[cdmlib.git] / cdmlib-persistence / src / main / java / eu / etaxonomy / cdm / database / CdmPersistentDataSource.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.cdm.database;
11
12 import static eu.etaxonomy.cdm.common.XmlHelp.getBeansRoot;
13 import static eu.etaxonomy.cdm.common.XmlHelp.insertXmlBean;
14 import static eu.etaxonomy.cdm.common.XmlHelp.insertXmlValueProperty;
15 import static eu.etaxonomy.cdm.common.XmlHelp.saveToXml;
16
17 import java.io.File;
18 import java.io.FileInputStream;
19 import java.io.FileNotFoundException;
20 import java.io.FileOutputStream;
21 import java.io.IOException;
22 import java.util.ArrayList;
23 import java.util.Enumeration;
24 import java.util.Iterator;
25 import java.util.List;
26 import java.util.Properties;
27
28 import javax.sql.DataSource;
29
30 import org.apache.log4j.Logger;
31 import org.hibernate.cache.internal.NoCachingRegionFactory;
32 import org.hibernate.cache.spi.RegionFactory;
33 import org.jdom.Attribute;
34 import org.jdom.Document;
35 import org.jdom.Element;
36 import org.jdom.output.Format;
37 import org.springframework.beans.MutablePropertyValues;
38 import org.springframework.beans.factory.config.BeanDefinition;
39 import org.springframework.beans.factory.config.PropertiesFactoryBean;
40 import org.springframework.beans.factory.support.AbstractBeanDefinition;
41 import org.springframework.beans.factory.support.RootBeanDefinition;
42
43 import com.mchange.v2.c3p0.ComboPooledDataSource;
44
45 import eu.etaxonomy.cdm.api.application.CdmApplicationUtils;
46 import eu.etaxonomy.cdm.common.CdmUtils;
47 import eu.etaxonomy.cdm.common.XmlHelp;
48 import eu.etaxonomy.cdm.database.types.IDatabaseType;
49 import eu.etaxonomy.cdm.model.name.NomenclaturalCode;
50
51
52 /**
53 * class to access an CdmDataSource
54 */
55 public class CdmPersistentDataSource extends CdmDataSourceBase{
56 private static final Logger logger = Logger.getLogger(CdmPersistentDataSource.class);
57
58 public static final String DATASOURCE_BEAN_POSTFIX = "DataSource";
59 public final static String DATASOURCE_FILE_NAME = "cdm.datasources.xml";
60 public final static String DATASOURCE_PATH = "/eu/etaxonomy/cdm/";
61
62 private final static Format format = Format.getPrettyFormat();
63
64 public enum DbProperties{
65 DRIVER_CLASS,
66 URL,
67 SERVER,
68 DATABASE,
69 PORT,
70 MODE,
71 FILEPATH,
72 USERNAME,
73 PASSWORD,
74 NOMENCLATURAL_CODE;
75
76 @Override
77 public String toString(){
78 switch (this){
79 case DRIVER_CLASS:
80 return "driverClassName";
81 case URL:
82 return "url";
83 case SERVER:
84 return "server";
85 case DATABASE:
86 return "database";
87 case PORT:
88 return "port";
89 case MODE:
90 return "mode";
91 case FILEPATH:
92 return "filePath";
93 case USERNAME:
94 return "username";
95 case PASSWORD:
96 return "password";
97 case NOMENCLATURAL_CODE:
98 return "nomenclaturalCode";
99 default:
100 throw new IllegalArgumentException( "Unknown enumeration type" );
101 }
102 }
103 }
104
105 /**
106 * The Datasource class that Spring will use to set up the connection to the database
107 */
108 private static String dataSourceClassName = ComboPooledDataSource.class.getName();
109 // we used dbcps BasicDataSource before
110 // private static String dataSourceClassName = BasicDataSource.class.getName();
111
112 //name
113 protected String dataSourceName;
114
115
116 /**
117 * Returns the default CdmDataSource
118 * @return the default CdmDataSource
119 * @throws DataSourceNotFoundException
120 */
121 public final static CdmPersistentDataSource NewDefaultInstance() throws DataSourceNotFoundException {
122 return NewInstance("default");
123 }
124
125
126 /**
127 * Returns the default CdmDataSource
128 * @return the default CdmDataSource
129 * @throws DataSourceNotFoundException
130 */
131 public final static CdmPersistentDataSource NewLocalHsqlInstance() throws DataSourceNotFoundException{
132 return NewInstance("localDefaultHsql");
133 }
134
135 /**
136 * Returns the CdmDataSource named by strDataSource
137 * @param strDataSource
138 * @return
139 */
140 public final static CdmPersistentDataSource NewInstance(String dataSourceName) throws DataSourceNotFoundException{
141 if (exists(dataSourceName)){
142 return new CdmPersistentDataSource(dataSourceName);
143 }else{
144 throw new DataSourceNotFoundException("Datasource not found: " + dataSourceName);
145 }
146 }
147
148 /**
149 * Private Constructor. Use NewXXX factory methods for creating a new instance of CdmDataSource!
150 * @param strDataSource
151 */
152 private CdmPersistentDataSource(String strDataSource){
153 dataSourceName = strDataSource;
154 }
155
156 /**
157 * Returns the name of the bean.
158 * @return
159 */
160 public String getName(){
161 return dataSourceName;
162 }
163
164
165 /**
166 * Returns the name of the bean Element in the xml config file.
167 * @return bean name
168 */
169 private static String getBeanName(String name){
170 return name == null? null : name + DATASOURCE_BEAN_POSTFIX;
171 }
172
173
174
175 public String getDatabase() {
176 return getDatabaseProperty(DbProperties.DATABASE);
177 }
178
179
180 public String getFilePath() {
181 //TODO null
182 return getDatabaseProperty(DbProperties.FILEPATH);
183 }
184
185
186 public H2Mode getMode() {
187 //TODO null
188 return H2Mode.fromString(getDatabaseProperty(DbProperties.MODE));
189 }
190
191
192 /* (non-Javadoc)
193 * @see eu.etaxonomy.cdm.database.ICdmDataSource#getNomenclaturalCode()
194 */
195 public NomenclaturalCode getNomenclaturalCode() {
196 // TODO null
197 return NomenclaturalCode.fromString(getDatabaseProperty(DbProperties.NOMENCLATURAL_CODE));
198 }
199
200 public int getPort() {
201 String port = CdmUtils.Nz(getDatabaseProperty(DbProperties.PORT));
202 if ("".equals(port)){
203 return -1;
204 }else{
205 //TODO exception if non integer
206 return Integer.valueOf(port);
207 }
208 }
209
210
211 public String getServer() {
212 return getDatabaseProperty(DbProperties.SERVER);
213 }
214
215 /**
216 * Returns the database type of the data source.
217 * @return the database type of the data source. Null if the bean or the driver class property does not exist or the driver class is unknown.
218 */
219 public DatabaseTypeEnum getDatabaseType(){
220 Element bean = getDatasourceBeanXml(this.dataSourceName);
221 if (bean == null){
222 return null;
223 }else{
224 Element driverProp = XmlHelp.getFirstAttributedChild(bean, "property", "name", "driverClassName");
225 if (driverProp == null){
226 logger.warn("Unknown property driverClass");
227 return null;
228 }else{
229 String strDriverClass = driverProp.getAttributeValue("value");
230 DatabaseTypeEnum dbType = DatabaseTypeEnum.getDatabaseEnumByDriverClass(strDriverClass);
231 return dbType;
232 }
233 }
234 }
235
236
237 /**
238 * Returns the database type of the data source.
239 * @return the database type of the data source. Null if the bean or the driver class property does not exist or the driver class is unknown.
240 */
241 protected String getDatabaseProperty(DbProperties property){
242 Element bean = getDatasourceBeanXml(this.dataSourceName);
243 String url;
244 String result = null;
245 if (bean != null){
246 result = getPropertyValue(bean, property.toString());
247 if (result == null){ //test if property is database, server or port which are included in the url
248 url = getPropertyValue(bean, DbProperties.URL.toString());
249 DatabaseTypeEnum dbTypeEnum = getDatabaseType();
250 if (dbTypeEnum != null){
251 IDatabaseType dbType = dbTypeEnum.getDatabaseType();
252 if (property.equals(DbProperties.DATABASE)){
253 result = dbType.getDatabaseNameByConnectionString(url);
254 }else if(property.equals(DbProperties.SERVER)){
255 result = dbType.getServerNameByConnectionString(url);
256 }else if(property.equals(DbProperties.PORT)){
257 result = String.valueOf(dbType.getPortByConnectionString(url));
258 }else{
259 logger.debug("Unknown property: " + property);
260 }
261 }
262 }
263 }
264 return result;
265 }
266
267 private String getPropertyValue(Element bean, String property){
268 Element driverProp = XmlHelp.getFirstAttributedChild(bean, "property", "name", property);
269 if (driverProp == null){
270 logger.debug("Unknown property: " + property);
271 return null;
272 }else{
273 String strProperty = driverProp.getAttributeValue("value");
274 return strProperty;
275 }
276 }
277
278
279
280 /**
281 * Returns the list of properties that are defined in the datasource
282 * @return
283 */
284 @SuppressWarnings("unchecked")
285 public List<Attribute> getDatasourceAttributes(){
286 List<Attribute> result = new ArrayList<Attribute>();
287 Element bean = getDatasourceBeanXml(this.dataSourceName);
288 if (bean == null){
289 return null;
290 }else{
291 result = bean.getAttributes();
292 }
293 return result;
294 }
295
296 /**
297 * Returns a defined property of the datasource
298 * @return the property of the data source. NULL if the datasource bean or the property does not exist.
299 */
300 public String getDatasourceProperty(DbProperties dbProp){
301 Element bean = getDatasourceBeanXml(this.dataSourceName);
302 if (bean == null){
303 return null;
304 }else{
305 Element elProperty = XmlHelp.getFirstAttributedChild(bean, "property", "name", dbProp.toString());
306 if (elProperty == null){
307 logger.warn("Unknown property: " + dbProp.toString());
308 return null;
309 }else{
310 String strValue = elProperty.getAttributeValue("value");
311 return strValue;
312 }
313 }
314 }
315
316
317 /**
318 * Returns the list of properties that are defined in the datasource
319 * @return
320 */
321 public Properties getDatasourceProperties(){
322 Properties result = new Properties();
323 Element bean = getDatasourceBeanXml(this.dataSourceName);
324 if (bean == null){
325 return null;
326 }else{
327 List<Element> elProperties = XmlHelp.getAttributedChildList(bean, "property", "name");
328 Iterator<Element> iterator = elProperties.iterator();
329 while(iterator.hasNext()){
330 Element next = iterator.next();
331 String strName = next.getAttributeValue("name");
332 String strValue = next.getAttributeValue("value");
333 result.put(strName, strValue);
334 }
335 }
336 return result;
337 }
338
339 /**
340 * Returns a BeanDefinition object of type DataSource that contains
341 * datsource properties (url, username, password, ...)
342 * @return
343 */
344 @SuppressWarnings("unchecked")
345 public BeanDefinition getDatasourceBean(){
346 DatabaseTypeEnum dbtype = DatabaseTypeEnum.getDatabaseEnumByDriverClass(getDatasourceProperty(DbProperties.DRIVER_CLASS));
347
348 AbstractBeanDefinition bd = new RootBeanDefinition(dbtype.getDataSourceClass());
349 //attributes
350 Iterator<Attribute> iterator = getDatasourceAttributes().iterator();
351 while(iterator.hasNext()){
352 Attribute attribute = iterator.next();
353 if (attribute.getName().equals("lazy-init")){
354 bd.setLazyInit(Boolean.valueOf(attribute.getValue()));
355 }
356 if (attribute.getName().equals("init-method")){
357 bd.setInitMethodName(attribute.getValue());
358 }
359 if (attribute.getName().equals("destroy-method")){
360 bd.setDestroyMethodName(attribute.getValue());
361 }
362 //Attribute attribute = iterator.next();
363 //bd.setAttribute(attribute.getName(), attribute.getValue());
364 }
365
366 //properties
367 MutablePropertyValues props = new MutablePropertyValues();
368 Properties persistentProperties = getDatasourceProperties();
369 Enumeration<String> keys = (Enumeration)persistentProperties.keys();
370 while (keys.hasMoreElements()){
371 String key = (String)keys.nextElement();
372
373 if (key.equals("nomenclaturalCode") && persistentProperties.getProperty(key).equals("ICBN")){
374 //bugfix for old nomenclatural codes, remove if fixed elsewhere, see https://dev.e-taxonomy.eu/trac/ticket/3658
375 props.addPropertyValue(key, NomenclaturalCode.ICNAFP.name());
376 }else{
377 props.addPropertyValue(key, persistentProperties.getProperty(key));
378 }
379 }
380
381 bd.setPropertyValues(props);
382 return bd;
383 }
384
385 /**
386 * @param hbm2dll
387 * @param showSql
388 * @return
389 */
390 public BeanDefinition getHibernatePropertiesBean(DbSchemaValidation hbm2dll){
391 boolean showSql = false;
392 boolean formatSql = false;
393 boolean registerSearchListener = false;
394 Class<? extends RegionFactory> cacheProviderClass = NoCachingRegionFactory.class;
395 return getHibernatePropertiesBean(hbm2dll, showSql, formatSql, registerSearchListener, cacheProviderClass);
396 }
397
398
399 /**
400 * @param hbm2dll
401 * @param showSql
402 * @return
403 */
404 public BeanDefinition getHibernatePropertiesBean(DbSchemaValidation hbm2dll, Boolean showSql, Boolean formatSql, Boolean registerSearchListener, Class<? extends RegionFactory> cacheProviderClass){
405 //Hibernate default values
406 if (hbm2dll == null){
407 hbm2dll = DbSchemaValidation.VALIDATE;
408 }
409 if (showSql == null){
410 showSql = false;
411 }
412 if (formatSql == null){
413 formatSql = false;
414 }
415 if (cacheProviderClass == null){
416 cacheProviderClass = NoCachingRegionFactory.class;
417 }
418 if(registerSearchListener == null){
419 registerSearchListener = false;
420 }
421
422 DatabaseTypeEnum dbtype = getDatabaseType();
423 AbstractBeanDefinition bd = new RootBeanDefinition(PropertiesFactoryBean.class);
424 MutablePropertyValues hibernateProps = new MutablePropertyValues();
425
426 Properties props = new Properties();
427 props.setProperty("hibernate.hbm2ddl.auto", hbm2dll.toString());
428 props.setProperty("hibernate.dialect", dbtype.getHibernateDialectCanonicalName());
429 props.setProperty("hibernate.cache.region.factory_class", cacheProviderClass.getName());
430 props.setProperty("hibernate.show_sql", String.valueOf(showSql));
431 props.setProperty("hibernate.format_sql", String.valueOf(formatSql));
432 props.setProperty("hibernate.search.autoregister_listeners", String.valueOf(registerSearchListener));
433
434 hibernateProps.addPropertyValue("properties",props);
435 bd.setPropertyValues(hibernateProps);
436 return bd;
437 }
438
439
440 /**
441 * Tests existing of the datsource in the according config file.
442 * @return true if a datasource with the given name exists in the according datasource config file.
443 */
444 public static boolean exists(String strDataSourceName){
445 Element bean = getDatasourceBeanXml(strDataSourceName);
446 return (bean != null);
447 }
448
449
450 /**
451 *
452 * @param strDataSourceName
453 * @param databaseTypeEnum
454 * @param server
455 * @param database
456 * @param port
457 * @param username
458 * @param password
459 * @param dataSourceClass
460 * @param initMethod
461 * @param destroyMethod
462 * @param startSilent
463 * @param startServer
464 * @param filePath
465 * @param mode
466 * @return
467 */
468 private static CdmPersistentDataSource save(String strDataSourceName,
469 DatabaseTypeEnum databaseTypeEnum,
470 String server,
471 String database,
472 String port,
473 String username,
474 String password,
475 Class<? extends DataSource> dataSourceClass,
476 String initMethod,
477 String destroyMethod,
478 Boolean startSilent,
479 Boolean startServer,
480 String filePath,
481 H2Mode mode,
482 NomenclaturalCode code
483 ){
484
485 int portNumber = "".equals(port) ? databaseTypeEnum.getDefaultPort() : Integer.valueOf(port);
486
487 ICdmDataSource dataSource = new CdmDataSource(databaseTypeEnum, server, database, portNumber, username, password, filePath, mode, code);
488
489 //root
490 Element root = getBeansRoot(getDataSourceInputStream());
491 if (root == null){
492 return null;
493 }
494 //bean
495 Element bean = XmlHelp.getFirstAttributedChild(root, "bean", "id", getBeanName(strDataSourceName));
496 if (bean != null){
497 bean.detach(); //delete old version if necessary
498 }
499 bean = insertXmlBean(root, getBeanName(strDataSourceName), dataSourceClass.getName());
500 //attributes
501 bean.setAttribute("lazy-init", "true");
502 if (initMethod != null) {bean.setAttribute("init-method", initMethod);}
503 if (destroyMethod != null) {bean.setAttribute("destroy-method", destroyMethod);}
504
505 //set properties
506 insertXmlValueProperty(bean, "driverClassName", databaseTypeEnum.getDriverClassName());
507
508 insertXmlValueProperty(bean, "url", databaseTypeEnum.getConnectionString(dataSource));
509 if (username != null) {insertXmlValueProperty(bean, "username", username );}
510 if (password != null) {insertXmlValueProperty(bean, "password", password );}
511 if (startSilent != null) {insertXmlValueProperty(bean, "startSilent", startSilent.toString() );}
512 if (startServer != null) {insertXmlValueProperty(bean, "startServer", startServer.toString() );}
513 if (filePath != null) {insertXmlValueProperty(bean, "filePath", filePath );}
514 if (mode != null) {insertXmlValueProperty(bean, "mode", mode.toString() );}
515 if (code != null) {insertXmlValueProperty(bean, "nomenclaturalCode", code.name());}
516
517 //save
518 saveToXml(root.getDocument(), getResourceDirectory(), DATASOURCE_FILE_NAME, format );
519 try {
520 return NewInstance(strDataSourceName) ;
521 } catch (DataSourceNotFoundException e) {
522 logger.error("Error when saving datasource");
523 return null;
524 }
525 }
526
527 /**
528 * @param strDataSourceName
529 * @param dataSource
530 * @param code
531 * @return
532 * the updated dataSource, null if not succesful
533 */
534 public static CdmPersistentDataSource update(String strDataSourceName,
535 ICdmDataSource dataSource) throws DataSourceNotFoundException, IllegalArgumentException{
536 delete(CdmPersistentDataSource.NewInstance(strDataSourceName));
537 return save(strDataSourceName, dataSource);
538 }
539
540 /**
541 * Saves a datasource to the datasource config file. If strDataSourceName differs a new dataSource
542 * will be created in config file. Use update() of real update functionality.
543 *
544 * @param strDataSourceName
545 * @param dataSource
546 * @return
547 */
548 public static CdmPersistentDataSource save(String strDataSourceName,
549 ICdmDataSource dataSource) throws IllegalArgumentException{
550
551 if(dataSource.getDatabaseType() == null){
552 new IllegalArgumentException("Database type not specified");
553 }
554
555 if(dataSource.getDatabaseType().equals(DatabaseTypeEnum.H2)){
556 Class<? extends DataSource> dataSourceClass = LocalH2.class;
557 if(dataSource.getMode() == null){
558 new IllegalArgumentException("H2 mode not specified");
559 }
560 return save(
561 strDataSourceName,
562 dataSource.getDatabaseType(),
563 "localhost",
564 getCheckedDataSourceParameter(dataSource.getDatabase()),
565 dataSource.getDatabaseType().getDefaultPort() + "",
566 getCheckedDataSourceParameter(dataSource.getUsername()),
567 getCheckedDataSourceParameter(dataSource.getPassword()),
568 dataSourceClass,
569 null, null, null, null,
570 getCheckedDataSourceParameter(dataSource.getFilePath()),
571 dataSource.getMode(),
572 dataSource.getNomenclaturalCode());
573 }else{
574
575 Class<? extends DataSource> dataSourceClass;
576 try {
577 dataSourceClass = (Class<? extends DataSource>) Class.forName(dataSourceClassName);
578
579 CdmPersistentDataSource persistendDatasource = save(
580 strDataSourceName,
581 dataSource.getDatabaseType(),
582 getCheckedDataSourceParameter(dataSource.getServer()),
583 getCheckedDataSourceParameter(dataSource.getDatabase()),
584 dataSource.getPort() + "",
585 getCheckedDataSourceParameter(dataSource.getUsername()),
586 getCheckedDataSourceParameter(dataSource.getPassword()),
587 dataSourceClass,
588 null, null, null, null, null, null,
589 dataSource.getNomenclaturalCode());
590
591 return persistendDatasource;
592 } catch (ClassNotFoundException e) {
593 logger.error("DataSourceClass not found - stopping application", e);
594 System.exit(-1);
595 }
596 // will never be reached
597 return null;
598 }
599 }
600
601 private static String getCheckedDataSourceParameter(String parameter) throws IllegalArgumentException{
602 if(parameter != null){
603 return parameter;
604 }else{
605 new IllegalArgumentException("Non obsolete paramater was assigned a null value: " + parameter);
606 return null;
607 }
608 }
609
610 /**
611 * Deletes a dataSource
612 * @param dataSource
613 */
614 public static void delete (CdmPersistentDataSource dataSource){
615 Element bean = getDatasourceBeanXml(dataSource.getName());
616 if (bean != null){
617 Document doc = bean.getDocument();
618 bean.detach();
619 saveToXml(doc, getDataSourceOutputStream(), format );
620 }
621 }
622
623
624 /**
625 * Returns a list of all datasources stored in the datasource config file
626 * @return all existing data sources
627 */
628 @SuppressWarnings("unchecked")
629 static public List<CdmPersistentDataSource> getAllDataSources(){
630 List<CdmPersistentDataSource> dataSources = new ArrayList<CdmPersistentDataSource>();
631
632 Element root = getBeansRoot(getDataSourceInputStream());
633 if (root == null){
634 return null;
635 }else{
636 List<Element> lsChildren = root.getChildren("bean", root.getNamespace());
637
638 for (Element elBean : lsChildren){
639 String strId = elBean.getAttributeValue("id");
640 if (strId != null && strId.endsWith(DATASOURCE_BEAN_POSTFIX)){
641 strId = strId.replace(DATASOURCE_BEAN_POSTFIX, "");
642 dataSources.add(new CdmPersistentDataSource(strId));
643 }
644 }
645 }
646 return dataSources;
647 }
648
649 public String getUsername(){
650 return getDatasourceProperty(DbProperties.USERNAME);
651 }
652
653 public String getPassword(){
654 return getDatasourceProperty(DbProperties.PASSWORD);
655 }
656
657
658 /* (non-Javadoc)
659 * @see java.lang.Object#toString()
660 */
661 public String toString(){
662 if (this.dataSourceName != null){
663 return dataSourceName;
664 }else{
665 return null;
666 }
667 }
668
669
670
671 /**
672 * Returns the datasource config file input stream.
673 * @return data source config file input stream
674 */
675 static protected FileInputStream getDataSourceInputStream(){
676 String dir = getResourceDirectory();
677 File file = new File(dir + File.separator + DATASOURCE_FILE_NAME);
678 return fileInputStream(file);
679 }
680
681
682 /**
683 * Returns the datasource config file outputStream.
684 * @return data source config file outputStream
685 */
686 static protected FileOutputStream getDataSourceOutputStream(){
687 String dir = getResourceDirectory();
688 File file = new File(dir + File.separator + DATASOURCE_FILE_NAME);
689 return fileOutputStream(file);
690 }
691
692 /**
693 * Returns the jdom Element representing the data source bean in the config file.
694 * @return
695 */
696 private static Element getDatasourceBeanXml(String strDataSourceName){
697 FileInputStream inStream = getDataSourceInputStream();
698 Element root = getBeansRoot(inStream);
699 if (root == null){
700 return null;
701 }else{
702 Element xmlBean = XmlHelp.getFirstAttributedChild(root, "bean", "id", getBeanName(strDataSourceName));
703 if (xmlBean == null){
704 //TODO warn or info
705 logger.debug("Unknown Element 'bean id=" +strDataSourceName + "' ");
706 }
707 return xmlBean;
708 }
709 }
710
711 // returns the directory containing the resources
712 private static String getResourceDirectory(){
713 try {
714 File f = CdmApplicationUtils.getWritableResourceDir();
715 return f.getPath();
716 } catch (IOException e) {
717 logger.error(e);
718 throw new RuntimeException(e);
719 }
720 }
721
722 static private FileInputStream fileInputStream(File file){
723 try {
724 FileInputStream fis = new FileInputStream(file);
725 return fis;
726 } catch (FileNotFoundException e) {
727 logger.warn("File " + file == null?"null":file.getAbsolutePath() + " does not exist in the file system");
728 return null;
729 }
730 }
731
732 static private FileOutputStream fileOutputStream(File file){
733 try {
734 FileOutputStream fos = new FileOutputStream(file);
735 return fos;
736 } catch (FileNotFoundException e) {
737 logger.warn("File " + (file == null?"null":file.getAbsolutePath()) + " does not exist in the file system");
738 return null;
739 }
740 }
741
742 public boolean equals(Object obj){
743 if (obj == null){
744 return false;
745 }else if (! CdmPersistentDataSource.class.isAssignableFrom(obj.getClass())){
746 return false;
747 }else{
748 CdmPersistentDataSource dataSource = (CdmPersistentDataSource)obj;
749 return (this.dataSourceName == dataSource.dataSourceName);
750 }
751
752 }
753 }