/* * $Id: Property.java,v 1.20 2009/01/21 10:03:33 valdas Exp $ Created on 21.12.2004 * * Copyright (C) 2004 Idega Software hf. All Rights Reserved. * * This software is the proprietary information of Idega hf. Use is subject to * license terms. */ package com.idega.util.reflect; import java.io.Serializable; import java.lang.reflect.Method; import java.util.List; import java.util.Locale; import java.util.logging.Level; import java.util.logging.Logger; import javax.el.ELContext; import javax.el.ValueExpression; import javax.faces.context.FacesContext; import com.idega.business.IBOLookup; import com.idega.business.chooser.helper.CalendarsChooserHelper; import com.idega.business.chooser.helper.GroupsChooserHelper; import com.idega.cal.bean.CalendarPropertiesBean; import com.idega.core.builder.business.BuilderService; import com.idega.core.builder.business.ICBuilderConstants; import com.idega.core.builder.data.ICPage; import com.idega.core.file.data.ICFile; import com.idega.core.localisation.business.ICLocaleBusiness; import com.idega.idegaweb.IWMainApplication; import com.idega.presentation.Image; import com.idega.presentation.PresentationObject; import com.idega.presentation.ui.PasswordInput; import com.idega.presentation.ui.handlers.IWDatePickerHandler; import com.idega.user.bean.PropertiesBean; import com.idega.user.data.Group; import com.idega.user.data.GroupHome; import com.idega.util.CoreUtil; import com.idega.util.StringUtil; /** * * This class holds an instance of a property with its value(s). * A property is in this case a setter method that has attatched set values (as a String or Object array).<br> * This is used in the Builder where properties are set via this class on PresentationObject instances. * * Last modified: $Date: 2009/01/21 10:03:33 $ by $Author: valdas $ * * @author <a href="mailto:tryggvi@idega.com">Tryggvi Larusson </a> * @version $Revision: 1.20 $ */ public class Property implements Serializable { private static final long serialVersionUID = 4451503674746022678L; private String propertyName; private Method method; private Object[] propertyValues; public Property() { // doing nothing, called by subclass } /** * Construct a property from a so called methodIdentifier that is used to construct a Method instance. * @param methodIdentifier a string in the format ':method:[modifierInt]:[classIdentifier]:[returnClass]:[methodName]:[parameterClass]:' , example: ':method:1:com.idega.presentation.Table:void:setWidth:java.lang.String:' */ public Property(String methodIdentifier) { this(methodIdentifier, null); } /** * Construct a property from a so called methodIdentifier that is used to construct a Method instance. * @param methodIdentifier a string in the format ':method:[modifierInt]:[classIdentifier]:[returnClass]:[methodName]:[parameterClass]:' , example: ':method:1:implied:void:setWidth:java.lang.String:' * @param declaringClass The class that the method is declared in. */ public Property(String methodIdentifier, Class<?> declaringClass) { if (declaringClass != null) { setMethod(getMethodFinder().getMethod(methodIdentifier, declaringClass)); } else { setMethod(getMethodFinder().getMethod(methodIdentifier)); } } /** * Construct a property from a given Method instance. * @param method */ public Property(Method method) { this.setMethod(method); } private MethodFinder getMethodFinder() { return MethodFinder.getInstance(); } /** * @return Returns the method. */ public Method getMethod() { return this.method; } /** * @param method * The method to set. */ public void setMethod(Method method) { this.method = method; } /** * @return Returns the propertyName. */ public String getPropertyName() { return this.propertyName; } /** * @param propertyName * The propertyName to set. */ public void setPropertyName(String propertyName) { this.propertyName = propertyName; } /** * @return Returns the propertyValues. */ public Object[] getPropertyValues() { return this.propertyValues; } /** * @param propertyValues * The propertyValues to set. */ public void setPropertyValues(String[] stringPropertyValues) { //this.propertyValues = propertyValues; Object[] args = new Object[stringPropertyValues.length]; Class<?>[] parameterTypes = getMethod().getParameterTypes(); for (int i = 0; i < parameterTypes.length; i++) { if (parameterTypes[i] != null) { String aString = stringPropertyValues[i]; try { args[i] = convertStringToObject(parameterTypes[i], aString); } catch (Exception e) { System.err.println("Error in property '" + this.method.toString()); e.printStackTrace(); } } } setPropertyValues(args); } /** * @param propertyValues * The propertyValues to set. */ public void setPropertyValues(Object[] propertyValues) { this.propertyValues = propertyValues; } /** * Sets the property on the object instance * * @param instance */ public void setPropertyOnInstance(Object instance) { try { getMethod().invoke(instance, getPropertyValues()); } catch (Exception e) { if (instance instanceof PresentationObject) { PresentationObject po = (PresentationObject) instance; System.err.println("Error in property '" + getMethod().toString() + "' for "+instance.getClass().getName()+" with ICObjectInstanceId=" + po.getICObjectInstanceID()); } else { System.err.println("Error in property '" + getMethod().toString() + "' for instance=" + instance.toString()); } e.printStackTrace(); } } @SuppressWarnings("unchecked") public static <T>T getValueFromExpression(String expression, Class<T> expectedResultType) { if (StringUtil.isEmpty(expression) || expectedResultType == null) { return null; } if (!expression.startsWith("#{") && !expression.endsWith("}")) { return null; } FacesContext fcContext = FacesContext.getCurrentInstance(); ELContext elContext = fcContext.getELContext(); ValueExpression ve = fcContext.getApplication().getExpressionFactory().createValueExpression(elContext, expression, expectedResultType); return (T) ve.getValue(elContext); } //Moved from ComponentPropertyHandler (in builder) protected Object convertStringToObject(Class<?> parameterType, String stringValue) throws Exception { Object argument = null; try { argument = getValueFromExpression(stringValue, parameterType); } catch(Exception e) { Logger.getLogger(this.getClass().getName()).log(Level.INFO, "Failed to get by value from ValueExpression by expression: " + stringValue, e); } if (argument != null) return argument; try { if (parameterType.equals(Integer.class) || parameterType.equals(Integer.TYPE)) { argument = Integer.valueOf(stringValue); } else if (parameterType.equals(String.class)) { argument = stringValue; } else if (parameterType.equals(Boolean.class) || parameterType.equals(Boolean.TYPE)) { argument = CoreUtil.getBooleanValueFromString(stringValue); } else if (parameterType.equals(Float.class) || parameterType.equals(Float.TYPE)) { argument = new Float(stringValue); } else if (parameterType.equals(ICPage.class)) { argument = ((com.idega.core.builder.data.ICPageHome) com.idega.data.IDOLookup.getHomeLegacy(ICPage.class)).findByPrimaryKeyLegacy(Integer.parseInt(stringValue)); } else if (parameterType.equals(ICFile.class)) { argument = ((com.idega.core.file.data.ICFileHome) com.idega.data.IDOLookup.getHome(ICFile.class)).findByPrimaryKey(new Integer( stringValue)); } else if (parameterType.equals(Image.class)) { argument = new Image(Integer.parseInt(stringValue)); } //REMOVE AND MAKE GENERIC! ask tryggvi and eiki else if (parameterType.equals(Group.class)) { argument = ((GroupHome) com.idega.data.IDOLookup.getHome(Group.class)).findByPrimaryKey(new Integer( stringValue.substring(stringValue.lastIndexOf('_') + 1, stringValue.length()))); } // added because of JSF methods else if (parameterType.equals(Object.class)) { // nothing to cast argument = stringValue; } else if (parameterType.equals(PasswordInput.class)) { argument = new PasswordInput(); if (stringValue != null) { ((PasswordInput) argument).setContent(stringValue); } } else if (parameterType.equals(List.class)) { argument = StringUtil.getValuesFromString(stringValue, ICBuilderConstants.BUILDER_MODULE_PROPERTY_VALUES_SEPARATOR); } else if (parameterType.equals(PropertiesBean.class)) { GroupsChooserHelper helper = new GroupsChooserHelper(); argument = helper.getExtractedPropertiesFromString(stringValue); } else if (parameterType.equals(CalendarPropertiesBean.class)) { CalendarsChooserHelper helper = new CalendarsChooserHelper(); argument = helper.getExtractedPropertiesFromString(stringValue); } else if (parameterType.equals(Locale.class)) { argument = ICLocaleBusiness.getLocaleFromLocaleString(stringValue); } else if (parameterType.equals(java.util.Date.class)) { argument = IWDatePickerHandler.getParsedDate(stringValue); } else if (parameterType.equals(ICPage.class)) { BuilderService builder = IBOLookup.getServiceInstance(IWMainApplication.getDefaultIWApplicationContext(), BuilderService.class); argument = builder.getICPage(stringValue); } } catch(Exception e) { Logger.getLogger(this.getClass().getName()).log(Level.INFO, "Failed to get value from expression: " + stringValue + ", expected type: " + parameterType); } return argument; } }