[Schmitzm-commits] r2278 - in trunk/schmitzm-hibernate/src/main: . java/de/schmitzm/db/hibernate java/de/schmitzm/db/hibernate/types resources resources/de resources/de/schmitzm resources/de/schmitzm/db resources/de/schmitzm/db/hibernate resources/de/schmitzm/db/hibernate/resource resources/de/schmitzm/db/hibernate/resource/locales
scm-commit at wald.intevation.org
scm-commit at wald.intevation.org
Sun Mar 24 12:15:47 CET 2013
Author: mojays
Date: 2013-03-24 12:15:47 +0100 (Sun, 24 Mar 2013)
New Revision: 2278
Added:
trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/DBUtil.java
trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateApplication.java
trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateSessionFactory.java
trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicType.java
trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicTypeInterface.java
trunk/schmitzm-hibernate/src/main/resources/
trunk/schmitzm-hibernate/src/main/resources/de/
trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/
trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/
trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/
trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/
trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/
trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle.properties
trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle_de.properties
Log:
schmitzm-hibernate: Generic HibernateSessionFactory and HibernateApplication, generic BasicType for enums
Added: trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/DBUtil.java
===================================================================
--- trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/DBUtil.java (rev 0)
+++ trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/DBUtil.java 2013-03-24 11:15:47 UTC (rev 2278)
@@ -0,0 +1,358 @@
+package de.schmitzm.db.hibernate;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Locale;
+
+import org.apache.log4j.Logger;
+import org.hibernate.Criteria;
+import org.hibernate.Session;
+import org.hibernate.criterion.Criterion;
+import org.hibernate.criterion.Order;
+import org.hibernate.criterion.Restrictions;
+
+import de.schmitzm.db.hibernate.types.BasicType;
+import de.schmitzm.db.hibernate.types.BasicTypeInterface;
+import de.schmitzm.db.hibernate.types.UniqueIDType;
+import de.schmitzm.lang.LangUtil;
+import de.schmitzm.lang.ResourceProvider;
+import de.schmitzm.swing.SwingUtil;
+
+/**
+ * Utility methods for hibernate.
+ *
+ * @author <a href="mailto:martin.schmitz at koeln.de">Martin Schmitz</a>
+ */
+public class DBUtil {
+ private static Logger LOGGER = LangUtil.createLogger(DBUtil.class);
+
+ /**
+ * {@link ResourceProvider} for the localization in the package
+ * {@code de.schmitzm.db.hibernate}.
+ */
+ public static ResourceProvider RESOURCE = ResourceProvider.newInstance(
+ LangUtil.extendPackagePath(DBUtil.class,
+ "resource.locales.HibernateResourceBundle"), Locale.ENGLISH);
+
+ /**
+ * Can hold a global {@link Session} used for updates. Should never
+ * be closed!
+ */
+ protected static Session GLOBAL_SESSION = null;
+
+ /**
+ * Returns the global {@link Session} which is used for internal/automatic
+ * database update, e.g. in {@link #getOrCreateBasicType(Class, String)}
+ * @param checkNull if {@code true} an exception is thrown if {@link #GLOBAL_SESSION}
+ * is not set or closed.
+ */
+ public static Session getGlobalSession(boolean checkNull) {
+ if ( checkNull ) {
+ if ( GLOBAL_SESSION == null )
+ throw new UnsupportedOperationException("DBUtil.GLOBAL_SESSION is not set.");
+ if ( !GLOBAL_SESSION.isOpen() )
+ throw new UnsupportedOperationException("DBUtil.GLOBAL_SESSION is not open.");
+ if ( !GLOBAL_SESSION.isConnected() )
+ throw new UnsupportedOperationException("DBUtil.GLOBAL_SESSION is not connected.");
+ }
+ return GLOBAL_SESSION;
+ }
+
+ /**
+ * Sets the global {@link Session} which is used for internal/automatic
+ * database update, e.g. in {@link #getOrCreateBasicType(Class, String)}
+ */
+ public static void setGlobalSession(Session session) {
+ GLOBAL_SESSION = session;
+ }
+
+ /**
+ * Checks whether two objects represent the same record. The ID is
+ * used for compare.
+ *
+ * @return {@code false}, if {@code o1 == null} and {@code o2 == null}
+ */
+ public static boolean equalsIdBased(UniqueIDType o1, UniqueIDType o2) {
+ if (o1 == null && o2 == null)
+ return false;
+ if (o1 == o2)
+ return true;
+ if (!(o1.getClass().equals(o2.getClass())))
+ return false;
+
+ // if bothe items are stored in DB, check the ID
+ if (o1.getId() != null && o2.getId() != null)
+ return o1.getId().equals(o2.getId());
+
+ // otherwise we expect the objects are unequal
+ return false;
+ }
+
+ /**
+ * Returns {@code o.getID().hashCode()} if the object is already persistent.
+ * @return {@link System#identityHashCode(Object)} for not-persistent objects
+ */
+ public static int hashCodeIdBased(UniqueIDType o) {
+ if (o == null)
+ throw new UnsupportedOperationException("DBUtil.hashCodeIdBased(.) can not be applied to NULL.");
+ if (o.getId() != null)
+ return o.getId().hashCode();
+ return System.identityHashCode(o);
+ }
+
+ /**
+ * Returns the description of a {@link BasicType}.
+ * @return {@code null} if the given instance is {@code null}
+ */
+ public static String getBasicTypeDescription(BasicType instance) {
+ if ( instance == null )
+ return null;
+ return instance.getDescription();
+ }
+
+ /**
+ * Creates a {@link BasicTypeInterface} instance (only object, NO persistence
+ * in database!). Expects that the given {@link BasicTypeInterface}
+ * sub-class has a parameter less constructor!
+ * @param basicType basic type to create the instance for
+ */
+ public static <E extends BasicTypeInterface> E createBasicTypeInstance(Class<E> basicType) {
+ try {
+ E basicTypeInstance = basicType.newInstance();
+ return basicTypeInstance;
+ } catch (Exception err) {
+ LOGGER.error(err.getMessage(), err);
+ return null;
+ }
+ }
+
+ /**
+ * Creates a {@link BasicTypeInterface} instance (only object, NO persistence
+ * in database!). Expects that the given {@link BasicType} sub-class has
+ * a parameter less constructor!
+ * @param basicType basic type to create the instance for
+ * @param desc description for the {@link BasicTypeInterface} instance
+ */
+ public static <E extends BasicTypeInterface> E createBasicType(Class<E> basicType, String desc) {
+ E instance = createBasicTypeInstance(basicType);
+ instance.setDescription(desc);
+ return instance;
+ }
+
+ /**
+ * Returns a {@link BasicTypeInterface} instance for the given description
+ * or creates it if it does not exist. The {@linkplain #getGlobalSession(boolean) global session}
+ * is used for possible database updates.
+ * @param basicType basic type to determine the instance for
+ * @param desc description for the {@link BasicTypeInterface} instance
+ * @see #getGlobalSession(boolean)
+ */
+ public static <E extends BasicTypeInterface> E getOrCreateBasicType(Class<E> basicType, String desc) {
+ return getOrCreateBasicType(basicType, desc, true);
+ }
+
+ /**
+ * Returns a {@link BasicTypeInterface} instance for the given description
+ * or creates it if it does not exist. The {@linkplain #getGlobalSession(boolean) global session}
+ * is used for possible database updates.
+ * @param basicType basic type to determine the instance for
+ * @param desc description for the {@link BasicTypeInterface} instance
+ * @param saveOrUpdate
+ * if {@code false}, no {@code Session.saveOrUpdate(.)} is performed (on possible
+ * creation). This has to be done explicitly later, e.g. in case when
+ * additional {@link BasicTypeInterface} attributes has to be
+ * filled before insert.
+ * @see #getGlobalSession(boolean)
+ */
+ public static <E extends BasicTypeInterface> E getOrCreateBasicType(Class<E> basicType, String desc, boolean saveOrUpdate) {
+ return getOrCreateBasicType(null, basicType, desc, saveOrUpdate);
+ }
+
+ /**
+ * Returns a {@link BasicTypeInterface} instance for the given description
+ * or creates it if it does not exist.
+ * @param basicType basic type to determine the instance for
+ * @param session session to use for update (if {@code null} the
+ * {@linkplain #getGlobalSession(boolean) global session} is used)
+ * @param desc description for the {@link BasicTypeInterface} instance
+ * @param saveOrUpdate
+ * if {@code false}, no {@code Session.saveOrUpdate(.)} is performed (on possible
+ * creation). This has to be done explicitly later, e.g. in case when
+ * additional {@link BasicTypeInterface} attributes has to be
+ * filled before insert.
+ * @see #getGlobalSession(boolean)
+ */
+ public static <E extends BasicTypeInterface> E getOrCreateBasicType(Session session, Class<E> basicType, String desc, boolean saveOrUpdate) {
+ if (org.apache.commons.lang.StringUtils.trimToNull(desc) == null)
+ return null;
+ if ( session == null )
+ session = getGlobalSession(true);
+ E instance = determineBasicType(basicType, desc);
+ if (instance == null) {
+ instance = createBasicTypeInstance(basicType);
+ instance.setDescription(desc);
+ if ( saveOrUpdate )
+ session.saveOrUpdate(instance);
+ }
+ return instance;
+ }
+
+ /**
+ * Checks whether a {@link BasicTypeInterface} instance is already persistent.
+ * If not it will be stored in database.
+ * @param session session to use for update (if {@code null} the
+ * {@linkplain #getGlobalSession(boolean) global session} is used)
+ * @param basicType basic type to check
+ * @return always {@code basicType}
+ */
+ public static <E extends BasicTypeInterface> E getOrCreateBasicType(Session session, E basicType) {
+ if ( basicType == null )
+ return null;
+ // if instance already has an id, it is already persistent
+ if ( basicType.getId() != null )
+ return basicType;
+
+ if ( session == null )
+ session = getGlobalSession(true);
+ session.persist(basicType);
+
+ return basicType;
+ }
+
+
+ /**
+ * Retrieves the first instances of a {@link BasicType} from database.
+ * The {@linkplain #getGlobalSession(boolean) global session} is used
+ * for database access.
+ * @param basicType basic type to determine an instance for
+ * @return {@code null} if the table is empty
+ */
+ public static <E extends BasicTypeInterface> E determineDefaultBasicType(Class<E> basicType) {
+ List<E> types = determineAllBasicTypes(basicType);
+ if (types.isEmpty())
+ return null;
+ return types.get(0);
+ }
+
+ /**
+ * Retrieves all instances of a type from database.
+ * @param session session to use for database access (if {@code null} the
+ * {@linkplain #getGlobalSession(boolean) global session} is used)
+ * @param type type to determine the instances for
+ */
+ public static <E extends Object> List<E> determineAllRecords(Session session, Class<E> type) {
+ return determineAllRecords(session,type, null, null);
+ }
+
+ /**
+ * Retrieves all instances of a type from database, which satisfies a filter.
+ * @param session session to use for database access (if {@code null} the
+ * {@linkplain #getGlobalSession(boolean) global session} is used)
+ * @param type type to determine the instances for
+ * @param filter filter to apply
+ */
+ public static <E extends Object> List<E> determineAllRecords(Session session, Class<E> type, Criterion filter, Order order) {
+ // if no session is specified, use the global session
+ if ( session == null )
+ session = getGlobalSession(true);
+
+ // Query muss in einer Transaktion erfolgen, damit die
+ // korrekten Daten ermittelt werden.
+ // -> Wenn keine Transaktion offen ist, eine neue beginnen
+ Criteria query = session.createCriteria(type);
+ if (filter != null)
+ query.add(filter);
+ if (order != null)
+ query.addOrder(order);
+
+ return (List<E>) query.list();
+ }
+
+ /**
+ * Retrieves all instances of a {@link BasicType} from database. The
+ * {@linkplain #getGlobalSession(boolean) global session} is used for database access.
+ * @param basicType type to determine the instances for
+ */
+ public static <E extends BasicTypeInterface> List<E> determineAllBasicTypes(Class<E> basicType) {
+ List<E> list = determineAllRecords(null, basicType, null, Order.asc(BasicType.DESCRIPTION_COL));
+ return list;
+ }
+
+ /**
+ * Retrieves all instances of a {@link BasicType} from database.
+ * @param session session to use for database access (if {@code null} the
+ * {@linkplain #getGlobalSession(boolean) global session} is used)
+ * @param basicType type to determine the instances for
+ */
+ public static <E extends BasicTypeInterface> List<E> determineAllBasicTypes(Session session, Class<E> basicType) {
+ return determineAllRecords(session, basicType, null, Order.asc(BasicType.DESCRIPTION_COL));
+ }
+
+ /**
+ * Retrieves all instances of a {@link BasicType} from database.
+ * @param session session to use for database access (if {@code null} the
+ * {@linkplain #getGlobalSession(boolean) global session} is used)
+ * @param basicType type to determine the instances for
+ * @param filter filter to apply
+ */
+ public static <E extends BasicTypeInterface> List<E> determineAllBasicTypes(Session session, Class<E> basicType, Criterion filter) {
+ return determineAllRecords(session, basicType, filter, Order.asc(BasicType.DESCRIPTION_COL));
+ }
+
+ /**
+ * Retrieves an instances of a {@link BasicType} from database with the specified description.
+ * The {@linkplain #getGlobalSession(boolean) global session} is used for database access.
+ */
+ public static <E extends BasicTypeInterface> E determineBasicType(Class<E> basicType, String description) {
+ Criteria query = getGlobalSession(true).createCriteria(basicType);
+ query.add(Restrictions.eq("bezeichnung", description));
+ List<E> resultList = (List<E>) query.list();
+
+ if (resultList.isEmpty())
+ return null;
+ if (resultList.size() > 1)
+ LOGGER.warn(LangUtil.getSimpleClassName(basicType) + " not unique for description: " + description);
+
+ return resultList.get(0);
+ }
+
+ /**
+ * Retrieves the description of all {@link BasicType} instances from database.
+ * The {@linkplain #getGlobalSession(boolean) global session} is used for database access.
+ */
+ public static <E extends BasicTypeInterface> List<String> determineAllBasicTypeDescriptions(Class<E> basicType) {
+ List<E> basicTypes = determineAllBasicTypes(basicType);
+ List<String> basicTypeDesc = new ArrayList<String>();
+ for (E basicTypeInst : basicTypes)
+ basicTypeDesc.add(basicTypeInst.getDescription());
+ return basicTypeDesc;
+ }
+
+ /**
+ * Returns the name of the discriminator column for a given type. This method expects that the types which are
+ * define the shared table ("InheritanceType.SINGLE_TABLE") hold a static String field "DESCR_COLUMN".
+ */
+ public static String getDisciminatorColumn(Class<?> type) {
+ try {
+ return (String) type.getDeclaredField("DESCR_COLUMN").get(null);
+ } catch (Exception err) {
+ // no discriminator column available
+ return null;
+ }
+ }
+
+ /**
+ * Returns the value of the discriminator column for a given type. This method expects that the types which are
+ * organized in a shared table ("InheritanceType.SINGLE_TABLE") hold a static String field "DESCR_VALUE".
+ */
+ public static String getDisciminatorValue(Class<?> type) {
+ try {
+ return (String) type.getDeclaredField("DESCR_VALUE").get(null);
+ } catch (Exception err) {
+ // no discriminator column available
+ return null;
+ }
+ }
+
+
+}
Added: trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateApplication.java
===================================================================
--- trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateApplication.java (rev 0)
+++ trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateApplication.java 2013-03-24 11:15:47 UTC (rev 2278)
@@ -0,0 +1,296 @@
+/**
+ * Copyright (c) 2009 Martin O. J. Schmitz.
+ *
+ * This file is part of the SCHMITZM library - a collection of utility
+ * classes based on Java 1.6, focusing (not only) on Java Swing
+ * and the Geotools library.
+ *
+ * The SCHMITZM project is hosted at:
+ * http://wald.intevation.org/projects/schmitzm/
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 3
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License (license.txt)
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * or try this link: http://www.gnu.org/licenses/lgpl.html
+ *
+ * Contributors:
+ * Martin O. J. Schmitz - initial API and implementation
+ * Stefan A. Tzeggai - additional utility classes
+ */
+package de.schmitzm.db.hibernate;
+
+import java.awt.Frame;
+
+import javax.swing.JOptionPane;
+
+import org.apache.log4j.Logger;
+
+import de.schmitzm.swing.Disposable;
+import de.schmitzm.swing.ExceptionDialog;
+import de.schmitzm.swing.SwingUtil;
+import de.schmitzm.swing.SwingWorker;
+import de.schmitzm.swing.input.InputOption;
+import de.schmitzm.swing.input.MultipleOptionPane;
+import de.schmitzm.temp.BaseTypeUtil;
+
+/**
+ * Super class for an application which connects to a database via
+ * hibernate.
+ * This class provides some useful, generic methods to deal with
+ * the database.
+ * @author Martin O.J. Schmitz
+ */
+public abstract class HibernateApplication implements Disposable {
+
+ /** Holds the {@link HibernateSessionFactory} which handles the
+ * database connection via hibernate. */
+ protected HibernateSessionFactory sessionFactory = null;
+
+ /** Holds the input options for database login. */
+ protected InputOption<?>[] dbConnectOptions = null;
+
+ /**
+ * Creates new application.
+ */
+ public HibernateApplication(HibernateSessionFactory sessionFactory) {
+ this.sessionFactory = sessionFactory;
+ }
+
+ /**
+ * Disposes the application.
+ */
+ @Override
+ public void dispose() {
+ // close open session
+ // HibernateSessionFactory.closeSession();
+ disconnectFromDatabase();
+ }
+
+ /**
+ * Returns the main frame of the application.
+ */
+ protected abstract Frame getMainFrame();
+
+ /**
+ * Returns the {@link HibernateSessionFactory} which controls the
+ * database connection for this application.
+ */
+ public HibernateSessionFactory getHibernateSessionFactory() {
+ return sessionFactory;
+ }
+
+
+ /**
+ * Checks whether a connection to the database exists.
+ */
+ public boolean isConnected() {
+ return sessionFactory.isConnected();
+ }
+
+ /**
+ * Returns the information of the last connection (application depended e.g.
+ * stored in properties). This implementation always returns {@code null}.
+ * Sub-classes can overwrite this method and return host (0), port (1), database
+ * name (2), user (3) and password (4).
+ */
+ protected String getLastConnectionSetting(int idx) {
+ switch (idx) {
+// case 0: return Props.INST.getString(Props.Keys.db_host);
+// case 1: return Props.INST.getString(Props.Keys.db_port, "5432");
+// case 2: return Props.INST.getString(Props.Keys.db_dbname);
+// case 3: return Props.INST.getString(Props.Keys.db_user);
+// case 4: return Props.STORE_DB_PASSWD ? Props.INST.getStringDecrypted(Props.Keys.db_passwd) : null;
+ }
+ return null;
+ }
+
+ /**
+ * This implementation does nothing.
+ * Sub-classes can overwrite this method and store the last connection
+ * information application depended e.g. in properties.
+ */
+ protected void setLastConnectionSettings(String host, Integer port, String dbname, String user, char[] passwd) {
+// Props.INST.set(Props.Keys.db_host, host);
+// Props.INST.set(Props.Keys.db_port, port);
+// Props.INST.set(Props.Keys.db_dbname, dbname);
+// Props.INST.set(Props.Keys.db_user, user);
+// if ( Props.STORE_DB_PASSWD )
+// Props.INST.setEncrypted(Props.Keys.db_passwd, new String(passwd));
+// Props.INST.store();
+ }
+
+ /**
+ * Returns whether password should be cleared (for security reasons)
+ * immediately after login (and not be stored in internal variables or
+ * properties).
+ * This default implementation always returns {@code true}. Sub-classes
+ * can overwrite this method to implement another behavior.
+ */
+ protected boolean clearPassword() {
+// return !Props.STORE_DB_PASSWD;
+ return true;
+ }
+
+ /**
+ * Called in case of error during connection procedure.
+ * This method does nothing. Sub-classes can overwrite this method do
+ * handle special exceptions, e.g. offer application update.
+ */
+ protected void handleConnectionException(Throwable err) {
+// if ( err instanceof ReleaseException ) {
+// checkApplicationUpdate(true,false);
+// }
+ }
+
+ /**
+ * Recreates the database completely. ALL DATA IS LOST!
+ * @return {@code false} if no new connection is established
+ */
+ public boolean initializeDatabase() {
+ if (isConnected())
+ disconnectFromDatabase();
+ boolean ret = connectToDatabase(true);
+ if (ret)
+ JOptionPane.showMessageDialog(getMainFrame(),
+ DBUtil.RESOURCE.getString("HibernateApplication.db.init.confirm.mess"),
+ DBUtil.RESOURCE.getString("HibernateApplication.db.init.title"),
+ JOptionPane.INFORMATION_MESSAGE);
+ return ret;
+ }
+
+ /**
+ * Creates a connection to the database, so that {@link #getSession()} returns an open session.
+ * Does nothing if a connection already exists.
+ * @return {@code false} if no new connection is established
+ */
+ public boolean connectToDatabase() {
+ return connectToDatabase(false);
+ }
+
+ /**
+ * Creates a connection to the database, so that {@link #getSession()} returns an open session. Does nothing if a
+ * connection already exists.
+ *
+ * @param forceCreate
+ * if {@code true} the database is completely rebuild; ALL DATA WILL BE LOST!
+ * @return {@code false} if no new connection is established
+ */
+ protected boolean connectToDatabase(final boolean forceCreate) {
+ if (isConnected())
+ return false;
+
+ // show dialog
+ if (dbConnectOptions == null) {
+ String server = getLastConnectionSetting(0);
+ Integer port = BaseTypeUtil.convertFromString(getLastConnectionSetting(1), Integer.class);
+ String databaseName = getLastConnectionSetting(2);
+ String userName = getLastConnectionSetting(3);
+ String pw = getLastConnectionSetting(4);
+ dbConnectOptions = SwingUtil.createDatabaseLoginDialogOptions(server,port,databaseName,
+ userName,pw).toArray(new InputOption<?>[0]);
+ }
+
+ // Show dialog until connection is established or
+ // dialog is canceled
+ while (true)
+ try {
+ Object[] optionValues = MultipleOptionPane.showMultipleInputDialog(
+ getMainFrame(),
+ DBUtil.RESOURCE.getString("HibernateApplication.db.conn.dialog.title"),
+ dbConnectOptions);
+ if (optionValues == null) {
+ // clear Password for security reasons
+ dbConnectOptions[4].setValue(null);
+ return false;
+ }
+ if (forceCreate) {
+ int ret = JOptionPane.showConfirmDialog(getMainFrame(),
+ DBUtil.RESOURCE.getString("HibernateApplication.db.init.warn.mess"),
+ DBUtil.RESOURCE.getString("HibernateApplication.db.init.title"),
+ JOptionPane.YES_NO_OPTION);
+ if (ret != JOptionPane.YES_OPTION) {
+ dbConnectOptions[4].setValue(null);
+ return false;
+ }
+ }
+
+ final String host = (String) optionValues[0];
+ final Integer port = (Integer) optionValues[1];
+ final String dbname = (String) optionValues[2];
+ final String user = (String) optionValues[3];
+ final char[] passwd = (char[]) optionValues[4];
+
+ // Aufbau der DB-Verbindung in einem Thread mit Dialog, der die
+ // GUI blockiert
+ SwingWorker.Work connectionWork = new SwingWorker.Work() {
+ @Override
+ public Object execute() throws Exception {
+ sessionFactory.rebuildSessionFactory(host, // Server
+ port, // Port
+ dbname, // DB-Name
+ user, // User
+ passwd,
+ forceCreate);
+ return sessionFactory.getSessionFactory();
+ }
+
+ @Override
+ public void performError(Throwable err) {
+ // nichts machen... wir behandeln die Exeception selbst
+ }
+ };
+ SwingWorker worker = new SwingWorker(connectionWork,
+ getMainFrame(),
+ DBUtil.RESOURCE.getString("HibernateApplication.db.conn.progress.mess"),
+ 0.5, 0.5);
+ // worker.getDialog().setDialogOption(StatusDialog.NONE_OPTION);
+ worker.start();
+ if (worker.getError() != null)
+ throw worker.getError();
+ if (worker.isCanceled())
+ continue;
+
+ // clear Password for security reasons
+ if ( clearPassword() )
+ dbConnectOptions[4].setValue(null);
+
+ // Nach erfolgreicher Verbindung die Benutezrdaten in die
+ // .properties schreiben
+ setLastConnectionSettings(host, port, dbname, user, passwd);
+ break;
+ } catch (Throwable err) {
+ // clear Password for security reasons
+ if ( clearPassword() )
+ dbConnectOptions[4].setValue(null);
+ ExceptionDialog.show(getMainFrame(), err);// , null,
+ // "Fehler bei der Datenbank-Anmeldung");
+ handleConnectionException(err);
+ }
+
+ return true;
+ }
+
+ /**
+ * Terminates the connection to the database.
+ *
+ * @return {@code false} if there was no open connection
+ */
+ public boolean disconnectFromDatabase() {
+ if (!isConnected())
+ return false;
+ sessionFactory.disconnectAllSessions();
+ sessionFactory.killSessionFactory();
+ return true;
+ }
+
+}
Added: trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateSessionFactory.java
===================================================================
--- trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateSessionFactory.java (rev 0)
+++ trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/HibernateSessionFactory.java 2013-03-24 11:15:47 UTC (rev 2278)
@@ -0,0 +1,597 @@
+package de.schmitzm.db.hibernate;
+
+import java.io.File;
+import java.io.Serializable;
+import java.sql.Connection;
+import java.sql.DatabaseMetaData;
+import java.sql.DriverManager;
+import java.sql.SQLException;
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.log4j.Logger;
+import org.hibernate.HibernateException;
+import org.hibernate.Query;
+import org.hibernate.SQLQuery;
+import org.hibernate.Session;
+import org.hibernate.cfg.AnnotationConfiguration;
+import org.hibernate.cfg.Environment;
+import org.hibernate.jdbc.Work;
+
+import de.schmitzm.io.IOUtil;
+import de.schmitzm.lang.LangUtil;
+import de.schmitzm.versionnumber.ReleaseControl;
+import de.schmitzm.versionnumber.ReleaseUpdater;
+
+/**
+ * Configures and provides access to Hibernate sessions, tied to the current thread of execution. Follows the Thread
+ * Local Session pattern, see {@link http://hibernate.org/42.html }.
+ */
+public abstract class HibernateSessionFactory {
+ private Logger LOGGER = LangUtil.createLogger(this);
+
+ private Session globalSession = null;
+ private Map<Object,Session> sessions = new HashMap<Object,Session>();
+
+ /** Indicates whether the applications deals with multiple sessions ({@code true})
+ * or only with the one global {@link Session} ({@code false}). */
+ protected boolean MULTIPLE_SESSIONS = true;
+
+ /**
+ * Internal variable to temporary hold the JDBC connection for {@link #getConnection()}.
+ */
+ private Connection tempConnection = null;
+
+ /**
+ * Location of hibernate.cfg.xml file. Location should be on the classpath as Hibernate uses #resourceAsStream style
+ * lookup for its configuration file. The default classpath location of the hibernate config file is in the default
+ * package. Use #setConfigFile() to update the location of the configuration file for the current session.
+ */
+ public static final String CONFIG_FILE_LOCATION = "/hibernate.cfg.xml";
+ private String configFile = null;
+ private AnnotationConfiguration configuration = null;
+ private org.hibernate.SessionFactory sessionFactory;
+
+ /**
+ * Creates a new session factory instance.
+ */
+ public HibernateSessionFactory(boolean multipleSessions) {
+ this(multipleSessions, CONFIG_FILE_LOCATION);
+ }
+
+ /**
+ * Creates a new session factory instance.
+ */
+ public HibernateSessionFactory(boolean multipleSessions, String configFile) {
+ this.MULTIPLE_SESSIONS = multipleSessions;
+ this.configFile = configFile;
+ }
+
+// /**
+// * return session factory
+// *
+// * session factory will be rebuilded in the next call
+// */
+// public static void setConfigFile(String configFile) {
+// sessionFactory = null;
+// }
+
+ /**
+ * return hibernate configuration
+ *
+ */
+ public AnnotationConfiguration getConfiguration() {
+ return configuration;
+ }
+
+// public static void setConfiguration(AnnotationConfiguration configuration) {
+// HibernateSessionFactory.configuration = configuration;
+// }
+
+
+ ////////////////////////////////////////////////////////////////////////////
+ ////////////////// FUNCTIONS TO MAINTAIN DB CONNECTION ///////////////////
+ ////////////////////////////////////////////////////////////////////////////
+
+ /**
+ * Returns the session factory.
+ * @return {@code null} if {@link #rebuildSessionFactory()} was not yet called
+ */
+ public org.hibernate.SessionFactory getSessionFactory() {
+ return sessionFactory;
+ }
+
+ /**
+ * Kills the session factory.
+ */
+ public void killSessionFactory() {
+ if (sessionFactory == null)
+ return;
+ sessionFactory.close();
+ sessionFactory = null;
+ }
+
+ /**
+ * Checks whether database connection is established.
+ * @return
+ */
+ public boolean isConnected() {
+ return sessionFactory != null && !sessionFactory.isClosed();
+ }
+
+ /**
+ * Rebuild hibernate session factory
+ */
+ public void rebuildSessionFactory() throws SQLException {
+ rebuildSessionFactory(null, null, null, null, (String) null, false);
+ }
+
+ /**
+ * Rebuild hibernate session factory
+ */
+ public void rebuildSessionFactory(String host, Integer port, String dbName, String user, char[] password)
+ throws SQLException {
+ rebuildSessionFactory(host, port, dbName, user, new String(password), false);
+ }
+
+ /**
+ * Rebuild hibernate session factory
+ */
+ public void rebuildSessionFactory(String host, Integer port, String dbName, String user, char[] password,
+ boolean forceCreate) throws SQLException {
+ rebuildSessionFactory(host, port, dbName, user, password != null ? new String(password) : null, forceCreate);
+ }
+
+ /**
+ * Rebuild hibernate session factory
+ */
+ public void rebuildSessionFactory(String host, Integer port, String dbName, String user, String password,
+ boolean forceCreate) throws SQLException {
+ // if host, port and dbName given, combine to URL
+ String connectionUrl = null;
+ if (host != null && port != null && dbName != null)
+ connectionUrl = createConnectionURL(host, port, dbName);
+
+ // first: get default configuration from file
+ configuration = new AnnotationConfiguration();
+ addAnnotations(configuration);
+
+ // use defaults from file
+ getConfiguration().configure(configFile);
+
+ if (connectionUrl != null)
+ getConfiguration().setProperty(Environment.URL, connectionUrl);
+ if (user != null)
+ getConfiguration().setProperty(Environment.USER, user);
+ if (password != null)
+ getConfiguration().setProperty(Environment.PASS, password);
+ // force create database
+ if (forceCreate) {
+ getConfiguration().setProperty(Environment.HBM2DDL_AUTO, "create");
+ }
+
+ // Leider "verschluckt" Hibernate etwaige Exceptions und es
+ // scheint keine moeglichkeit zu geben, dass diese abfangbar
+ // durchgereicht werden...
+ // http://www.java-forum.org/datenbankprogrammierung/85763-sqlexception-fangen-beim-verbinden-hibernate.html
+ // -> hier erstmal "antesten", ob die Anmelde-Informationen korrekt sind
+ checkDatabaseConnection(getConfiguration().getProperty(Environment.URL),
+ getConfiguration().getProperty(Environment.USER), getConfiguration().getProperty(Environment.PASS));
+
+
+ // check whether program version fits the program version
+ // required by the database schema
+ checkApplicationRelease();
+
+ // KLAPPT NICHT SO WIE GEDACHT
+ // // Wenn DB neu erstellt wird, alte DB zunaecht loeschen,
+ // // um Konflikte mit manuell angelegten Constraints
+ // // zu vermeiden
+ // if ( "create".equals(getConfiguration().getProperty(Environment.HBM2DDL_AUTO)) )
+ // dropAndRecreateDatabase(host, port, dbName, user, password);
+
+ sessionFactory = getConfiguration().buildSessionFactory();
+ if ("create".equals(getConfiguration().getProperty(Environment.HBM2DDL_AUTO))) {
+ initAdditionalConstraints();
+ }
+ }
+
+ /**
+ * Checks whether the running application version is compatible to existing
+ * database scheme. This method is called by {@link #rebuildSessionFactory(String, Integer, String, String, String, boolean)}
+ * after database connection check and before {@link #rebuildSessionFactory()} call.
+ * This default implementation does nothing. Sub-classes can overwrite this method
+ * to implement application depended check.
+ */
+ protected void checkApplicationRelease() {
+// RELEASE_CONTROL.checkApplicationRelease(getConfiguration().getProperty(Environment.URL),
+// getConfiguration().getProperty(Environment.USER),
+// getConfiguration().getProperty(Environment.PASS));
+ }
+
+ ////////////////////////////////////////////////////////////////////////////
+ ///////////////////// FUNCTIONS TO MAINTAIN SESSIONS /////////////////////
+ ////////////////////////////////////////////////////////////////////////////
+ /**
+ * Closes all open sessions.
+ */
+ public void disconnectAllSessions() {
+ for (Session s : sessions.values())
+ if ( s != null && s.isConnected() ) {
+ s.disconnect();
+ s.close();
+ }
+ if ( globalSession != null && globalSession.isConnected() ) {
+ globalSession.disconnect();
+ globalSession.close();
+ }
+ // remove session references
+ globalSession = null;
+ sessions.clear();
+ }
+
+ /**
+ * Closes a session if it is still open.
+ */
+ public void closeSession(Session session) {
+ if ( session == null )
+ return;
+ if ( session.isOpen() )
+ session.close();
+ }
+
+ /**
+ * Returns an open global session which can be used to
+ * read-only queries. For database updated the
+ * "caller" should create and maintain its own session.
+ */
+ public Session getSession() {
+ return getSession(true);
+ }
+
+ /**
+ * Returns a global session which can be used to
+ * read-only queries. For database updated the
+ * "caller" should create and maintain its own session.
+ * @param renew indicates whether a new session is created
+ * if the current global session is
+ * closed (or does not yet exist). If {@code false},
+ * {@code null} or a closed session may be returned!
+ */
+ public Session getSession(boolean renew) {
+ if ( !isConnected() )
+ return null;
+ if ( globalSession == null || !globalSession.isOpen() ) {
+ if ( renew )
+ globalSession = getSessionFactory().openSession();
+ }
+ return globalSession;
+ }
+
+ /**
+ * Returns an open session for an individual object.
+ */
+ public Session getSession(Object key) {
+ return getSession(key,true);
+ }
+
+ /**
+ * Returns a session for an individual object.
+ * @param renew indicates whether a new session is created
+ * if the current session for the object is
+ * closed (or does not yet exist). If {@code false},
+ * {@code null} or a closed session may be returned!
+ */
+ public Session getSession(Object key, boolean renew) {
+ if ( !isConnected() )
+ return null;
+ // if no key is given, return the global session
+ if ( key == null )
+ return getSession(renew);
+
+ Session session = null;
+ if ( MULTIPLE_SESSIONS )
+ // use individual sessions for every key
+ session = sessions.get(key);
+ else
+ // use always the one global session
+ session = getSession();
+
+
+ if ( session == null || !session.isOpen() ) {
+ if ( renew ) {
+ session = getSessionFactory().openSession();
+ sessions.put(key, session);
+ }
+ }
+ if ( session != null && session.isOpen() )
+ beginTransactionIfNeeded(session);
+
+ return session;
+ }
+
+ /**
+ * Closes a session for an individual object and removes it
+ * from session cache.
+ */
+ public void disposeSession(Object key) {
+ Session session = getSession(key,false);
+ if ( session != null ) {
+ session.flush(); // ??
+ session.clear();
+ session.disconnect();
+ closeSession(session);
+ sessions.remove(key);
+ session = null;
+ }
+ }
+
+ /**
+ * Starts a new transaction if no transaction is active.
+ *
+ * @param deferredChecks
+ * if {@code true}, all constraints are set to <i>deferred</i>, so that they are not checked before
+ * transaction end (<b>Note:</b> it depends on the database and version, which constraints are effected
+ * by the <i>deferred</i> setting!!)
+ */
+ private void beginTransactionIfNeeded(Session session, boolean deferredChecks) {
+ if (session == null)
+ throw new UnsupportedOperationException(
+ "Transaktion kann nicht begonnen werden, da keine Session zur Verfuegung steht!");
+ if (session.getTransaction() == null || !session.getTransaction().isActive())
+ session.beginTransaction();
+ if (deferredChecks) {
+ SQLQuery query = session.createSQLQuery("SET CONSTRAINTS ALL DEFERRED");
+ query.executeUpdate();
+ }
+ }
+
+ /**
+ * Starts a new transaction for the global session
+ * if no transaction is active.
+ *
+ * @param deferredChecks
+ * if {@code true}, all constraints are set to <i>deferred</i>, so that they are not checked before
+ * transaction end (<b>Note:</b> it depends on the database and version, which constraints are effected
+ * by the <i>deferred</i> setting!!)
+ */
+ private void beginTransactionIfNeeded(boolean deferredChecks) {
+ beginTransactionIfNeeded(getSession(), deferredChecks);
+ }
+
+
+ /**
+ * Starts a new transaction with immediate constraint checking.
+ */
+ public void beginTransactionIfNeeded(Session session) {
+ beginTransactionIfNeeded(session,false);
+ }
+
+ /**
+ * Starts a new transaction with immediate constraint checking.
+ */
+ public void beginTransactionIfNeeded(Object key) {
+ Session session = getSession(key);
+ beginTransactionIfNeeded(session,false);
+ }
+
+ /**
+ * Starts a new transaction for the global session with
+ * immediate constraint checking.
+ */
+ public void beginTransactionIfNeeded() {
+ beginTransactionIfNeeded(getSession());
+ }
+
+ ////////////////////////////////////////////////////////////////////////////
+ /////////////////////////// UTILITY FUNCTIONS ////////////////////////////
+ ////////////////////////////////////////////////////////////////////////////
+
+ /**
+ * Calls {@code getSession().get(..)} and casts the returning object automatically to the called type.
+ */
+ public <E> E get(Class<E> type, Serializable objectID) {
+ return (E) getSession().get(type, objectID);
+ }
+
+ /**
+ * Combines hostname, port and database name to a connection URL. "jdbc:postgres" is currently used as protocoll
+ * everytime.
+ *
+ * @param host
+ * hostname
+ * @param port
+ * port
+ * @param dbName
+ * database name
+ */
+ public static String createConnectionURL(String host, int port, String dbName) {
+ String connectionUrl = "jdbc:postgresql://" + host + ":" + port + "/" + dbName + "?characterEncoding=utf8";
+ return connectionUrl;
+ }
+
+ /**
+ * Testet an, ob die Anmelde-Informationen korrekt sind und wirft gegebenfalls eine Exception. Ist alles ok,
+ * passiert nichts.
+ *
+ * @param host
+ * Server
+ * @param port
+ * Port
+ * @param dbName
+ * Datenbank-Name
+ * @param user
+ * Benutzer
+ * @param password
+ * Passwort
+ * @throws SQLException
+ */
+ public static void checkDatabaseConnection(String host, Integer port, String dbName, String user, String password)
+ throws SQLException {
+ String connectionUrl = createConnectionURL(host, port, dbName);
+ checkDatabaseConnection(connectionUrl, user, password);
+ }
+
+ /**
+ * Testet an, ob die Anmelde-Informationen korrekt sind und wirft gegebenfalls eine Exception. Ist alles ok,
+ * passiert nichts.
+ *
+ * @param dbURL
+ * Protokoll + Server + Port + Datenbank-Name
+ * @param user
+ * Benutzer
+ * @param password
+ * Passwort
+ * @throws SQLException
+ */
+ public static void checkDatabaseConnection(String dbURL, String user, String password) throws SQLException {
+ Connection conn = DriverManager.getConnection(dbURL, user, password);
+ conn.close();
+ }
+
+ /**
+ * Returns the JDBC {@link Connection} of the current session.
+ *
+ * @return {@code null} if there is no session established
+ */
+ public Connection getConnection() {
+ if (!isConnected())
+ return null;
+
+ Work work = new Work() {
+ @Override
+ public void execute(Connection connection) throws SQLException {
+ tempConnection = connection;
+ }
+ };
+ beginTransactionIfNeeded();
+ getSession().doWork(work);
+ return tempConnection;
+ }
+
+ /**
+ * Returns the JDBC {@link Connection} of the current session.
+ *
+ * @return {@code null} if there is no session established
+ */
+ public DatabaseMetaData getConnectionMetadata() {
+ Connection conn = getConnection();
+ if (conn == null)
+ return null;
+ try {
+ return conn.getMetaData();
+ } catch (SQLException err) {
+ return null;
+ }
+
+ }
+
+// /**
+// * Liefert die Anzahl der offenen Sessions fuer die aktuelle
+// * Verbindung des Users.
+// * @deprecated funktioniert irgendwie nicht, liefert nur bei der
+// * ersten Anfrage das richtige Ergebnis; danach immer
+// * wieder das gleiche...
+// */
+// public int getOpenSessionCount() throws SQLException {
+// int count = 0;
+//
+//
+// // klappt leider so nicht...
+// count = PGUtil.getOpenSessionCount(
+// getConnection(),
+// Props.INST.getString(Props.Keys.db_dbname),
+// DBUtil.getCurrentUser());
+//
+//// // TEST MIT Abfrage direkt im doWork(.)
+//// final AtomicInteger countA = new AtomicInteger();
+//// Work work = new Work() {
+//// @Override
+//// public void execute(Connection connection) throws SQLException {
+//// int c = PGUtil.getOpenSessionCount(
+//// connection,
+//// Props.get(Props.Keys.db_dbname),
+//// DBUtil.getCurrentUser());
+//// countA.set(c);
+//// }
+//// };
+//// HibernateSessionFactory.getSession().doWork(work);
+//// count = countA.get();
+//
+//// // TEST MIT HIBERNATE-SQL STATT Statement ueber Connection...
+//// // ... leider ohne Erfolg
+//// SQLQuery q = HibernateSessionFactory.getSession().createSQLQuery("SELECT COUNT(*) FROM pg_stat_activity WHERE datname = ? and usename = ?");
+//// q.setString(0, Props.get(Props.Keys.db_dbname) );
+//// q.setString(1, DBUtil.getCurrentUser());
+//// BigInteger result = (BigInteger)q.uniqueResult();
+//// count = result.intValue();
+//
+// System.err.println(count);
+// return count;
+// }
+
+ ////////////////////////////////////////////////////////////////////////////
+ ////////////////////// INTERNAL UTILITY FUNCTIONS ////////////////////////
+ ////////////////////////////////////////////////////////////////////////////
+
+ /**
+ * Adds all annotated classes (types) to the configuaration. Has to implemented
+ * application dependend.
+ */
+ protected abstract void addAnnotations(AnnotationConfiguration configuration);
+
+ /**
+ * Adds additional constraints (via SQL), which can not be created automatically by hibernate. If their creation
+ * fails (probably because they already exist), it is ignored.
+ * This default implementation does nothing. Sub-classes can overwrite this method to implement
+ * create database constraints on database initialisation.
+ */
+ protected void initAdditionalConstraints() {
+// executeInTransactionIgnoreEx(new Runnable() {
+// @Override
+// public void run() {
+// new PermissionManagement().setupPermissions();
+// }
+// });
+
+ }
+
+ /**
+ * Executes some work within an transaction.
+ */
+ protected void executeInTransactionIgnoreEx(Runnable runnable) {
+ beginTransactionIfNeeded();
+ try {
+ runnable.run();
+ getSession().getTransaction().commit();
+ } catch (HibernateException e) {
+ getSession().getTransaction().rollback();
+ } finally {
+ beginTransactionIfNeeded();
+ }
+ }
+
+
+ /**
+ * Creates a {@link Query} to add a primary key constraint a table ("ALTER TABLE ADD CONSTRAINT...").
+ * @param type
+ * data type
+ * @param attr
+ * attribute names the primary key is created for
+ */
+ protected Query createPrimaryKeyConstraintQuery(String tableName, String... attr) {
+ String constrName = "PK_"+tableName;
+ String queryStr = "ALTER TABLE " + tableName + " ADD CONSTRAINT \"" + constrName + "\" PRIMARY KEY (";
+ for (int i=0; i<attr.length; i++) {
+ if ( i>0 )
+ queryStr += ", ";
+ queryStr += attr[i];
+ }
+ queryStr += ")";
+ LOGGER.debug("Primary Key Query: " + queryStr);
+// getSession().createSQLQuery("alter table "+Mitarbeiter.TABLENAME+"_mailverteiler add constraint pk_"+Mitarbeiter.TABLENAME+"_mailverteiler PRIMARY KEY (mitarbeiter_id, mailverteiler_id)").executeUpdate();
+ return getSession().createSQLQuery(queryStr);
+
+ }
+
+}
\ No newline at end of file
Added: trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicType.java
===================================================================
--- trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicType.java (rev 0)
+++ trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicType.java 2013-03-24 11:15:47 UTC (rev 2278)
@@ -0,0 +1,89 @@
+package de.schmitzm.db.hibernate.types;
+
+import javax.persistence.Column;
+import javax.persistence.Inheritance;
+import javax.persistence.InheritanceType;
+import javax.persistence.MappedSuperclass;
+
+import de.schmitzm.db.hibernate.DBUtil;
+import de.schmitzm.lang.LangUtil;
+
+
+/**
+ * Super type for all Basic types. Basic types represent enums on the database.
+ * They are identified by a (unique) ID and a description.
+ *
+ * @author <a href="mailto:martin.schmitz at koeln.de">Martin Schmitz</a>
+ */
+ at MappedSuperclass
+ at Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
+public abstract class BasicType extends AbstractUniqueIDType implements BasicTypeInterface {
+ /** Name of the description column */
+ public static final String DESCRIPTION_COL = "description";
+ /** Size of the description column. Can be redefined by sub class using:<br>
+ * <code> @AttributeOverrides({
+ * @AttributeOverride(name = BasicType.DESCRIPTION_COL, column = @Column(length=...))
+ * })
+ * </code>
+ * */
+ public static final int DESCRIPTION_SIZE = 100;
+
+ /** The "readable" value of the enum value. */
+ @Column(name = DESCRIPTION_COL, length = DESCRIPTION_SIZE, nullable = false)
+ protected String description;
+
+ /**
+ * Creates a new enum value with empty description.
+ */
+ public BasicType() {
+ this("");
+ }
+
+ /**
+ * Creates a new enum value.
+ */
+ public BasicType(String desc) {
+ setDescription(desc);
+ }
+
+ /**
+ * Returns the "readable" description of the enum value.
+ */
+ public String getDescription() {
+ return description;
+ }
+
+ /**
+ * Sets the "readable" description of the enum value.
+ */
+ public void setDescription(String bezeichnung) {
+ this.description = LangUtil.trimToSize(bezeichnung,DESCRIPTION_SIZE);
+ }
+
+ /**
+ * Returns {@link #getDescription()}.
+ */
+ public String toString() {
+ return getDescription();
+ }
+
+ /**
+ * Checks whether a {@link BasicType} instances equals
+ * another by ID.
+ */
+ public boolean equals(Object object) {
+ if ( !(object instanceof BasicType) )
+ return false;
+ return DBUtil.equalsIdBased(this, (BasicType)object);
+ }
+
+ /**
+ * Returns {@code getID().hashCode()} if the instance is already
+ * persistent (has an ID). For inpersistent instances the method
+ * returns {@link System#identityHashCode(Object)}.
+ */
+ @Override
+ public int hashCode() {
+ return DBUtil.hashCodeIdBased(this);
+ }
+}
Added: trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicTypeInterface.java
===================================================================
--- trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicTypeInterface.java (rev 0)
+++ trunk/schmitzm-hibernate/src/main/java/de/schmitzm/db/hibernate/types/BasicTypeInterface.java 2013-03-24 11:15:47 UTC (rev 2278)
@@ -0,0 +1,20 @@
+package de.schmitzm.db.hibernate.types;
+
+
+/**
+ * Super type for all Basic types. Basic types represent enums on the database.
+ * They are identified by a (unique) ID and a description.
+ *
+ * @author <a href="mailto:martin.schmitz at koeln.de">Martin Schmitz</a>
+ */
+public interface BasicTypeInterface extends UniqueIDType {
+ /**
+ * Returns the "readable" description of the enum value.
+ */
+ public String getDescription();
+
+ /**
+ * Sets the "readable" description of the enum value.
+ */
+ public void setDescription(String desc);
+}
Added: trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle.properties
===================================================================
--- trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle.properties (rev 0)
+++ trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle.properties 2013-03-24 11:15:47 UTC (rev 2278)
@@ -0,0 +1,38 @@
+##########
+#This file is part of the SCHMITZM library - a collection of utility
+#classes based on Java 1.6, focussing (not only) on Java Swing
+#and the Geotools library.
+#
+#The SCHMITZM project is hosted at:
+#http://wald.intevation.org/projects/schmitzm/
+#
+#This program is free software; you can redistribute it and/or
+#modify it under the terms of the GNU Lesser General Public License
+#as published by the Free Software Foundation; either version 3
+#of the License, or (at your option) any later version.
+#
+#This program is distributed in the hope that it will be useful,
+#but WITHOUT ANY WARRANTY; without even the implied warranty of
+#MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+#GNU General Public License for more details.
+#
+#You should have received a copy of the GNU Lesser General Public License (license.txt)
+#along with this program; if not, write to the Free Software
+#Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+#or try this link: http://www.gnu.org/licenses/lgpl.html
+#
+#Contributors:
+# Martin O. J. Schmitz - initial API and implementation
+# Stefan A. Tzeggai - additional utility classes
+##########
+# ---------------------------------------------------------------
+# ------ Default Translations (english) for GUI components ------
+# ------ in Package de.schmitzm.db.hibernate ------
+# ---------------------------------------------------------------
+HibernateApplication.db.init.title=Database initialization
+HibernateApplication.db.init.warn.mess=WARNING! During initialize all data will be deleted! Continue anyway?
+HibernateApplication.db.init.confirm.mess=Database was rebuild
+HibernateApplication.db.conn.dialog.title=Database connection
+HibernateApplication.db.conn.progress.mess=Establishing database connection ...
+
+
Added: trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle_de.properties
===================================================================
--- trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle_de.properties (rev 0)
+++ trunk/schmitzm-hibernate/src/main/resources/de/schmitzm/db/hibernate/resource/locales/HibernateResourceBundle_de.properties 2013-03-24 11:15:47 UTC (rev 2278)
@@ -0,0 +1,37 @@
+##########
+#This file is part of the SCHMITZM library - a collection of utility
+#classes based on Java 1.6, focussing (not only) on Java Swing
+#and the Geotools library.
+#
+#The SCHMITZM project is hosted at:
+#http://wald.intevation.org/projects/schmitzm/
+#
+#This program is free software; you can redistribute it and/or
+#modify it under the terms of the GNU Lesser General Public License
+#as published by the Free Software Foundation; either version 3
+#of the License, or (at your option) any later version.
+#
+#This program is distributed in the hope that it will be useful,
+#but WITHOUT ANY WARRANTY; without even the implied warranty of
+#MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+#GNU General Public License for more details.
+#
+#You should have received a copy of the GNU Lesser General Public License (license.txt)
+#along with this program; if not, write to the Free Software
+#Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+#or try this link: http://www.gnu.org/licenses/lgpl.html
+#
+#Contributors:
+# Martin O. J. Schmitz - initial API and implementation
+# Stefan A. Tzeggai - additional utility classes
+##########
+# ---------------------------------------------------------------
+# ------ Germal Translations for GUI components ------
+# ------ in Package de.schmitzm.db.hibernate ------
+# ---------------------------------------------------------------
+HibernateApplication.db.init.title=Datenbank-Initialisierung
+HibernateApplication.db.init.warn.mess=ACHTUNG! Bei der Initialisierung werden alle Daten gelöscht! Fortfahren?
+HibernateApplication.db.init.confirm.mess=Datenbank wurde neu aufgebaut
+HibernateApplication.db.conn.dialog.title=Datenbank-Anmeldung
+HibernateApplication.db.conn.progress.mess=Datenbank-Verbindung wird aufgebaut...
+
More information about the Schmitzm-commits
mailing list