Mercurial > hg > release > thermostat-1.6
view storage/core/src/main/java/com/redhat/thermostat/storage/core/experimental/statement/StatementUtils.java @ 2049:a92d602216ad
Update copyright license headers for 2017
PR3290
Reviewed-by: jerboaa
Review-thread: http://icedtea.classpath.org/pipermail/thermostat/2017-January/021974.html
author | Andrew Azores <aazores@redhat.com> |
---|---|
date | Tue, 17 Jan 2017 12:19:56 -0500 |
parents | 31f274ab27a5 |
children |
line wrap: on
line source
/* * Copyright 2012-2017 Red Hat, Inc. * * This file is part of Thermostat. * * Thermostat is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published * by the Free Software Foundation; either version 2, or (at your * option) any later version. * * Thermostat 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 General Public License * along with Thermostat; see the file COPYING. If not see * <http://www.gnu.org/licenses/>. * * Linking this code with other modules is making a combined work * based on this code. Thus, the terms and conditions of the GNU * General Public License cover the whole combination. * * As a special exception, the copyright holders of this code give * you permission to link this code with independent modules to * produce an executable, regardless of the license terms of these * independent modules, and to copy and distribute the resulting * executable under terms of your choice, provided that you also * meet, for each linked independent module, the terms and conditions * of the license of that module. An independent module is a module * which is not derived from or based on this code. If you modify * this code, you may extend this exception to your version of the * library, but you are not obligated to do so. If you do not wish * to do so, delete this exception statement from your version. */ package com.redhat.thermostat.storage.core.experimental.statement; import com.redhat.thermostat.storage.core.Persist; import com.redhat.thermostat.storage.core.PreparedStatement; import com.redhat.thermostat.storage.model.Pojo; import java.beans.BeanInfo; import java.beans.IntrospectionException; import java.beans.Introspector; import java.beans.PropertyDescriptor; import java.lang.annotation.Annotation; import java.lang.reflect.Method; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; import java.util.HashMap; import java.util.List; import java.util.Map; /** * */ public class StatementUtils { static boolean isPersistent(PropertyDescriptor desc) { return hasAnnotation(desc, Persist.class); } static boolean isIndexed(PropertyDescriptor desc) { return hasAnnotation(desc, Indexed.class); } static <T extends Pojo> String getDocument(Class<T> pojoClass) { if (!pojoClass.isAnnotationPresent(Category.class)) { return null; } return pojoClass.getAnnotation(Category.class).value(); } static boolean hasAnnotation(PropertyDescriptor desc, Class<? extends Annotation> annotation) { Method readMethod = desc.getReadMethod(); boolean hasRead = (readMethod != null && readMethod.isAnnotationPresent(annotation)); Method writeMethod = desc.getWriteMethod(); boolean hasWrite = (writeMethod != null && writeMethod.isAnnotationPresent(annotation)); return hasRead && hasWrite; } public static Map<String, FieldDescriptor> createDescriptorMap(List<FieldDescriptor> descriptors) { Map<String, FieldDescriptor> map = new HashMap<>(); for (FieldDescriptor desc : descriptors) { map.put(desc.getName(), desc); } return map; } public static <T extends Pojo> List<FieldDescriptor> createDescriptors(Class<T> pojoClass) { try { BeanInfo info = Introspector.getBeanInfo(pojoClass); PropertyDescriptor[] props = info.getPropertyDescriptors(); List<FieldDescriptor> descriptors = new ArrayList<>(); for (PropertyDescriptor desc : props) { if (StatementUtils.isPersistent(desc)) { FieldDescriptor descriptor = new FieldDescriptor(); descriptor.setType(desc.getPropertyType()); descriptor.setName(desc.getName()); descriptor.setIndexed(StatementUtils.isIndexed(desc)); descriptors.add(descriptor); } } // Afaik it's not specified that methods are returned or listed in // any particular order by Introspector.getBeanInfo, so if we don't // sort, we may end up with two differently ordered lists in two // different calls to this method. // This is a problem because the prepated statement API doesn't // check if two statements are the same if fields are sorted in // random order, it only considers two statements the same if // their string representation completely matches; // it also make the code depending on FieldDescriptor easier to // write if it can count on the ordering being always consistent Collections.sort(descriptors, new Comparator<FieldDescriptor>() { @Override public int compare(FieldDescriptor o1, FieldDescriptor o2) { return o1.getName().compareTo(o2.getName()); } }); return Collections.unmodifiableList(descriptors); } catch (IntrospectionException e) { throw new RuntimeException(e); } } static <T extends Pojo> Value getValue(T bean, FieldDescriptor descriptor) { try { PropertyDescriptor property = new PropertyDescriptor(descriptor.getName(), bean.getClass()); Method method = property.getReadMethod(); method.setAccessible(true); return new Value(method.invoke(bean, new Object[0])); } catch (Exception e) { throw new RuntimeException(e); } } static <T extends Pojo> void setData(PreparedStatement<T> prepared, Value value, int index) { Class type = value.get().getClass(); if (type.isAssignableFrom(int.class) || type.isAssignableFrom(Integer.class)) { prepared.setInt(index, ((Integer) value.get()).intValue()); } else if (type.isAssignableFrom(long.class) || type.isAssignableFrom(Long.class)) { prepared.setLong(index, ((Long) value.get()).longValue()); } else if (type.isAssignableFrom(boolean.class) || type.isAssignableFrom(Boolean.class)) { prepared.setBoolean(index, ((Boolean) value.get()).booleanValue()); } else if (type.isAssignableFrom(String.class)) { prepared.setString(index, (String) value.get()); } } }