package core;

import java.text.ParseException;

import org.hibernate.QueryException;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.metadata.ClassMetadata;
import org.hibernate.type.Type;

import util.Parser;

import foo.bar.entities.Event;

/**
 * 
 * http://docs.jboss.org/hibernate/orm/5.1/userguide/html_single/
 * Hibernate_User_Guide.html#bootstrap
 * 
 * http://stackoverflow.com/questions/25684785/how-to-read-database-
 * configuration-parameter-using-properties-file-in-hibernate
 * 
 * @author Fernando Felix do Nascimento Junior
 *
 */
public class HibernateUtil {

	private static SessionFactory sessionFactory;

	public static SessionFactory getSessionFactory() {
		return sessionFactory;
	}

	public static void setSessionFactory(SessionFactory sessionFactory) {
		HibernateUtil.sessionFactory = sessionFactory;
	}

	/**
	 * Build a standard session factory for the application based on settings of
	 * the default Hibernate configuration.
	 * 
	 * @return A standard session factory
	 */
	public static SessionFactory buildSessionFactory() {
		if (sessionFactory == null) {
			sessionFactory = createConfiguration("hibernate.cfg.xml").buildSessionFactory();
		}
		return sessionFactory;
	}

	/**
	 * Creates a Hibernate configuration based on a resource file wit Annotated
	 * classes registered dynamically.
	 * 
	 * @param resource
	 *            The resource name. If none given, Hibernate handles the
	 *            default configuration resource.
	 * @see HibernateUtil#registerAnnoteatedClass(Configuration)
	 * 
	 * @return A Hibernate configuration
	 */
	public static Configuration createConfiguration(String resource) {
		Configuration configuration = new Configuration();
		if (resource == null)
			configuration.configure();
		else
			configuration.configure(resource);
		registerAnnoteatedClass(configuration);
		return configuration;
	}

	/**
	 * Adds the entity model classes into a configuration file that will be used
	 * by Hibernate to map.
	 * 
	 * @param configuration
	 */
	public static void registerAnnoteatedClass(Configuration configuration) {
		configuration.addAnnotatedClass(Event.class);
	}

	/**
	 * Retorna o tipo da propriedade de uma entidade recursivamente
	 * 
	 * @param c
	 *            A classe da entidade
	 * @param propertyName
	 *            O nome da propriedade (ex.: veiculo.modelo.codigo))
	 * @return O tipo da propriedade
	 * @throws QueryException
	 */
	public static Type getPropertyType(Class<?> c, String propertyName) throws QueryException {

		if (propertyName == null)
			throw new QueryException("Property name passed cannot be null or empty");

		// se for uma propriedade singular
		if (!propertyName.contains(".")) {
			return getClassMetadata(c).getPropertyType(propertyName);
		} // se não ...

		// seta a propriedade principal (a primeira)
		Type mainProperty = getClassMetadata(c).getPropertyType(propertyName.split("\\.")[0]);

		// se realmente for uma propriedade e se for um tipo de entidade
		if (mainProperty.isEntityType()) {

			String subProperties = propertyName.substring(propertyName.indexOf(".") + 1, propertyName.length());

			// verifica se as subpropriedades sao validas pelo seu
			// gerenciador
			return getPropertyType(mainProperty.getReturnedClass(), subProperties);
		} else
			throw new QueryException("Property " + propertyName.split("\\.")[0] + " is not a entity.");
	}

	/**
	 * Retorna os metadados de uma entidade
	 * 
	 * @param c
	 *            A entidade
	 * @return Se nao for um entidade, retornara null
	 */
	@SuppressWarnings("deprecation")
	public static ClassMetadata getClassMetadata(Class<?> c) {
		return sessionFactory.getClassMetadata(c);
	}

	/**
	 * Converte um valor conforme a classe retornada do tipo de uma propriedade
	 * de uma determinada entidade
	 * 
	 * @param c
	 *            A entidade
	 * @param propertyName
	 *            O nome da propriedade
	 * @param value
	 *            O valor a ser convertido
	 * @return O valor convertido
	 * @throws ParseException
	 */
	public static Object parseValue(Class<?> c, String propertyName, Object value) throws ParseException {

		Type type = getPropertyType(c, propertyName);

		if (value.getClass().equals(type.getReturnedClass()))
			return value;
		else
			return Parser.parseValue(type.getReturnedClass(), value);
	}

	/**
	 * Coverte um valor conforme a classe retornada de um tipo de propriedade
	 * 
	 * @param type
	 *            O tipo de propriedade
	 * @param value
	 *            O valor a ser convertido
	 * @return O valor convertido
	 * @throws ParseException
	 */
	public static Object parseValue(Type type, Object value) throws ParseException {
		return Parser.parseValue(type.getReturnedClass(), value);
	}

}

@@ -19,245 +19,76 @@
 ort 
-java.text.ParseException;%0A%0Aimport org.hibernate.QueryException;%0Aimport org.hibernate.SessionFactory;%0Aimport org.hibernate.cfg.Configuration;%0Aimport org.hibernate.metadata.ClassMetadata;%0Aimport org.hibernate.type.Type;%0A%0Aimport util.Parser
+org.hibernate.SessionFactory;%0Aimport org.hibernate.cfg.Configuration
 ;%0A%0Ai
@@ -2018,2578 +2018,6 @@
 %09%7D%0A%0A
-%09/**%0A%09 * Retorna o tipo da propriedade de uma entidade recursivamente%0A%09 * %0A%09 * @param c%0A%09 *            A classe da entidade%0A%09 * @param propertyName%0A%09 *            O nome da propriedade (ex.: veiculo.modelo.codigo))%0A%09 * @return O tipo da propriedade%0A%09 * @throws QueryException%0A%09 */%0A%09public static Type getPropertyType(Class%3C?%3E c, String propertyName) throws QueryException %7B%0A%0A%09%09if (propertyName == null)%0A%09%09%09throw new QueryException(%22Property name passed cannot be null or empty%22);%0A%0A%09%09// se for uma propriedade singular%0A%09%09if (!propertyName.contains(%22.%22)) %7B%0A%09%09%09return getClassMetadata(c).getPropertyType(propertyName);%0A%09%09%7D // se n%C3%A3o ...%0A%0A%09%09// seta a propriedade principal (a primeira)%0A%09%09Type mainProperty = getClassMetadata(c).getPropertyType(propertyName.split(%22%5C%5C.%22)%5B0%5D);%0A%0A%09%09// se realmente for uma propriedade e se for um tipo de entidade%0A%09%09if (mainProperty.isEntityType()) %7B%0A%0A%09%09%09String subProperties = propertyName.substring(propertyName.indexOf(%22.%22) + 1, propertyName.length());%0A%0A%09%09%09// verifica se as subpropriedades sao validas pelo seu%0A%09%09%09// gerenciador%0A%09%09%09return getPropertyType(mainProperty.getReturnedClass(), subProperties);%0A%09%09%7D else%0A%09%09%09throw new QueryException(%22Property %22 + propertyName.split(%22%5C%5C.%22)%5B0%5D + %22 is not a entity.%22);%0A%09%7D%0A%0A%09/**%0A%09 * Retorna os metadados de uma entidade%0A%09 * %0A%09 * @param c%0A%09 *            A entidade%0A%09 * @return Se nao for um entidade, retornara null%0A%09 */%0A%09@SuppressWarnings(%22deprecation%22)%0A%09public static ClassMetadata getClassMetadata(Class%3C?%3E c) %7B%0A%09%09return sessionFactory.getClassMetadata(c);%0A%09%7D%0A%0A%09/**%0A%09 * Converte um valor conforme a classe retornada do tipo de uma propriedade%0A%09 * de uma determinada entidade%0A%09 * %0A%09 * @param c%0A%09 *            A entidade%0A%09 * @param propertyName%0A%09 *            O nome da propriedade%0A%09 * @param value%0A%09 *            O valor a ser convertido%0A%09 * @return O valor convertido%0A%09 * @throws ParseException%0A%09 */%0A%09public static Object parseValue(Class%3C?%3E c, String propertyName, Object value) throws ParseException %7B%0A%0A%09%09Type type = getPropertyType(c, propertyName);%0A%0A%09%09if (value.getClass().equals(type.getReturnedClass()))%0A%09%09%09return value;%0A%09%09else%0A%09%09%09return Parser.parseValue(type.getReturnedClass(), value);%0A%09%7D%0A%0A%09/**%0A%09 * Coverte um valor conforme a classe retornada de um tipo de propriedade%0A%09 * %0A%09 * @param type%0A%09 *            O tipo de propriedade%0A%09 * @param value%0A%09 *            O valor a ser convertido%0A%09 * @return O valor convertido%0A%09 * @throws ParseException%0A%09 */%0A%09public static Object parseValue(Type type, Object value) throws ParseException %7B%0A%09%09return Parser.parseValue(type.getReturnedClass(), value);%0A%09%7D%0A%0A
 %7D%0A

Revert HibernateUtil.java