Search in sources :

Example 11 with PojoMetadata

use of org.apache.felix.ipojo.parser.PojoMetadata in project felix by apache.

the class ProvidedServiceHandlerTest method testServiceDetectionSuperClass.

public void testServiceDetectionSuperClass() throws ConfigurationException {
    String classname = "org.apache.felix.ipojo.handlers.providedservice.ComponentTestWithSuperClass";
    Element metadata = new Element("component", "");
    Element manipulation = new Element("manipulation", "");
    metadata.addAttribute(new Attribute("classname", classname));
    Element provides = new Element("provides", "");
    provides.addAttribute(new Attribute("specifications", "java.beans.SimpleBeanInfo"));
    metadata.addElement(provides);
    metadata.addElement(manipulation);
    manipulation.addAttribute(new Attribute("classname", classname));
    manipulation.addAttribute(new Attribute("super", "java.beans.SimpleBeanInfo"));
    Mockito.when(factory.getPojoMetadata()).thenReturn(new PojoMetadata(metadata));
    Mockito.when(factory.getClassName()).thenReturn(classname);
    handler.initializeComponentFactory(desc, metadata);
    System.out.println(metadata);
}
Also used : Attribute(org.apache.felix.ipojo.metadata.Attribute) Element(org.apache.felix.ipojo.metadata.Element) PojoMetadata(org.apache.felix.ipojo.parser.PojoMetadata)

Example 12 with PojoMetadata

use of org.apache.felix.ipojo.parser.PojoMetadata in project felix by apache.

the class ConfigurationHandler method initializeComponentFactory.

/**
 * Initialize the component type.
 *
 * @param desc     : component type description to populate.
 * @param metadata : component type metadata.
 * @throws ConfigurationException : metadata are incorrect.
 * @see org.apache.felix.ipojo.Handler#initializeComponentFactory(org.apache.felix.ipojo.architecture.ComponentTypeDescription, org.apache.felix.ipojo.metadata.Element)
 */
public void initializeComponentFactory(ComponentTypeDescription desc, Element metadata) throws ConfigurationException {
    Element[] confs = metadata.getElements("Properties", "");
    if (confs == null) {
        return;
    }
    Element[] configurables = confs[0].getElements("Property");
    for (int i = 0; configurables != null && i < configurables.length; i++) {
        String fieldName = configurables[i].getAttribute("field");
        String methodName = configurables[i].getAttribute("method");
        String paramIndex = configurables[i].getAttribute("constructor-parameter");
        if (fieldName == null && methodName == null && paramIndex == null) {
            throw new ConfigurationException("Malformed property : The property needs to contain" + " at least a field, a method or a constructor-parameter");
        }
        String name = configurables[i].getAttribute("name");
        if (name == null) {
            if (fieldName == null && methodName != null) {
                name = methodName;
            } else if (fieldName == null && paramIndex != null) {
                // Extract the name from the arguments.
                MethodMetadata[] constructors = getFactory().getPojoMetadata().getConstructors();
                if (constructors.length != 1) {
                    throw new ConfigurationException("Cannot infer the property name injected in the constructor " + "parameter #" + paramIndex + " - add the `name` attribute");
                } else {
                    int idx = Integer.valueOf(paramIndex);
                    if (constructors[0].getMethodArgumentNames().length > idx) {
                        name = constructors[0].getMethodArgumentNames()[idx];
                    } else {
                        throw new ConfigurationException("Cannot infer the property name injected in the constructor " + "parameter #" + paramIndex + " - not enough argument in the constructor :" + constructors[0].getArguments());
                    }
                }
            } else {
                name = fieldName;
            }
            // Add the type to avoid configure checking
            configurables[i].addAttribute(new Attribute("name", name));
        }
        String value = configurables[i].getAttribute("value");
        // Detect the type of the property
        PojoMetadata manipulation = getFactory().getPojoMetadata();
        String type = null;
        if (methodName != null) {
            MethodMetadata[] method = manipulation.getMethods(methodName);
            if (method.length == 0) {
                type = configurables[i].getAttribute("type");
                if (type == null) {
                    throw new ConfigurationException("Malformed property : The type of the property cannot be discovered, add a 'type' attribute");
                }
            } else {
                if (method[0].getMethodArguments().length != 1) {
                    throw new ConfigurationException("Malformed property :  The method " + methodName + " does not have one argument");
                }
                type = method[0].getMethodArguments()[0];
                // Add the type to avoid configure checking
                configurables[i].addAttribute(new Attribute("type", type));
            }
        } else if (fieldName != null) {
            FieldMetadata field = manipulation.getField(fieldName);
            if (field == null) {
                throw new ConfigurationException("Malformed property : The field " + fieldName + " does not exist in the implementation class");
            }
            type = field.getFieldType();
            // Add the type to avoid configure checking
            configurables[i].addAttribute(new Attribute("type", type));
        } else if (paramIndex != null) {
            int index = Integer.parseInt(paramIndex);
            type = configurables[i].getAttribute("type");
            MethodMetadata[] cts = manipulation.getConstructors();
            // we the index 'index'.
            if (type == null && cts.length > 0 && cts[0].getMethodArguments().length > index) {
                type = cts[0].getMethodArguments()[index];
            } else if (type == null) {
                // Applied only if type was not determined.
                throw new ConfigurationException("Cannot determine the type of the property " + index + ", please use the type attribute");
            }
            configurables[i].addAttribute(new Attribute("type", type));
        }
        // Is the property set to immutable
        boolean immutable = false;
        String imm = configurables[i].getAttribute("immutable");
        immutable = imm != null && imm.equalsIgnoreCase("true");
        boolean mandatory = false;
        String man = configurables[i].getAttribute("mandatory");
        mandatory = man != null && man.equalsIgnoreCase("true");
        PropertyDescription pd;
        if (value == null) {
            // Cannot be immutable if we have no value.
            pd = new PropertyDescription(name, type, null, false);
        } else {
            pd = new PropertyDescription(name, type, value, immutable);
        }
        if (mandatory) {
            pd.setMandatory();
        }
        desc.addProperty(pd);
    }
}
Also used : PropertyDescription(org.apache.felix.ipojo.architecture.PropertyDescription) FieldMetadata(org.apache.felix.ipojo.parser.FieldMetadata) Attribute(org.apache.felix.ipojo.metadata.Attribute) Element(org.apache.felix.ipojo.metadata.Element) PojoMetadata(org.apache.felix.ipojo.parser.PojoMetadata) MethodMetadata(org.apache.felix.ipojo.parser.MethodMetadata)

Example 13 with PojoMetadata

use of org.apache.felix.ipojo.parser.PojoMetadata in project felix by apache.

the class DependencyHandler method configure.

/**
 * Configure the handler.
 *
 * @param componentMetadata : the component type metadata
 * @param configuration     : the instance configuration
 * @throws ConfigurationException : one dependency metadata is not correct.
 * @see org.apache.felix.ipojo.Handler#configure(org.apache.felix.ipojo.metadata.Element, java.util.Dictionary)
 */
public void configure(Element componentMetadata, Dictionary configuration) throws ConfigurationException {
    PojoMetadata manipulation = getFactory().getPojoMetadata();
    boolean atLeastOneField = false;
    // Create the dependency according to the component metadata
    Element[] deps = componentMetadata.getElements("Requires");
    // Get instance filters.
    Dictionary filtersConfiguration = getRequiresFilters(configuration.get("requires.filters"));
    Dictionary fromConfiguration = (Dictionary) configuration.get("requires.from");
    for (int i = 0; deps != null && i < deps.length; i++) {
        // Create the dependency metadata
        final Element dependencyElement = deps[i];
        String field = dependencyElement.getAttribute("field");
        String serviceSpecification = getServiceSpecificationAttribute(dependencyElement);
        String opt = dependencyElement.getAttribute("optional");
        boolean optional = opt != null && opt.equalsIgnoreCase("true");
        String defaultImpl = dependencyElement.getAttribute("default-implementation");
        String exception = dependencyElement.getAttribute("exception");
        String to = dependencyElement.getAttribute("timeout");
        int timeout = 0;
        if (to != null) {
            timeout = Integer.parseInt(to);
        }
        String agg = dependencyElement.getAttribute("aggregate");
        boolean aggregate = agg != null && agg.equalsIgnoreCase("true");
        String identity = dependencyElement.getAttribute("id");
        String nul = dependencyElement.getAttribute("nullable");
        boolean nullable = nul == null || nul.equalsIgnoreCase("true");
        boolean isProxy = isProxy(dependencyElement);
        BundleContext context = getFacetedBundleContext(dependencyElement);
        String filter = computeFilter(dependencyElement, filtersConfiguration, fromConfiguration, aggregate, identity);
        Filter fil = createAndCheckFilter(filter);
        Class spec = null;
        if (serviceSpecification != null) {
            spec = DependencyMetadataHelper.loadSpecification(serviceSpecification, getInstanceManager().getContext());
        }
        int policy = DependencyMetadataHelper.getPolicy(dependencyElement);
        Comparator cmp = DependencyMetadataHelper.getComparator(dependencyElement, getInstanceManager().getGlobalContext());
        Dependency dep = new Dependency(this, field, spec, fil, optional, aggregate, nullable, isProxy, identity, context, policy, cmp, defaultImpl, exception);
        dep.setTimeout(timeout);
        // Look for dependency callback :
        addCallbacksToDependency(dependencyElement, dep);
        // Add the constructor parameter if needed
        String paramIndex = dependencyElement.getAttribute("constructor-parameter");
        if (paramIndex != null) {
            int index = Integer.parseInt(paramIndex);
            dep.addConstructorInjection(index);
        }
        // Check the dependency, throws an exception on error.
        DependencyConfigurationChecker.ensure(dep, dependencyElement, manipulation);
        m_dependencies.add(dep);
        if (dep.getField() != null) {
            getInstanceManager().register(manipulation.getField(dep.getField()), dep);
            atLeastOneField = true;
        }
    }
    if (atLeastOneField) {
        // Does register only if we have fields
        MethodMetadata[] methods = manipulation.getMethods();
        for (MethodMetadata method : methods) {
            for (Dependency dep : m_dependencies) {
                getInstanceManager().register(method, dep);
            }
        }
        // Also track the inner class methods
        for (String inner : manipulation.getInnerClasses()) {
            MethodMetadata[] meths = manipulation.getMethodsFromInnerClass(inner);
            if (meths != null) {
                for (MethodMetadata method : meths) {
                    for (Dependency dep : m_dependencies) {
                        getInstanceManager().register(method, inner, dep);
                    }
                }
            }
        }
    }
    // Initialize the description.
    m_description = new DependencyHandlerDescription(this, getDependencies());
    manageContextSources(configuration);
}
Also used : Element(org.apache.felix.ipojo.metadata.Element) Filter(org.osgi.framework.Filter) PojoMetadata(org.apache.felix.ipojo.parser.PojoMetadata) MethodMetadata(org.apache.felix.ipojo.parser.MethodMetadata) BundleContext(org.osgi.framework.BundleContext)

Example 14 with PojoMetadata

use of org.apache.felix.ipojo.parser.PojoMetadata in project felix by apache.

the class LifecycleCallbackHandler method configure.

/**
 * Configure the handler.
 * @param metadata : the component type metadata
 * @param configuration : the instance configuration
 * @throws ConfigurationException : one callback metadata is not correct (either the transition or the method are not correct).
 * @see org.apache.felix.ipojo.Handler#configure(org.apache.felix.ipojo.metadata.Element, java.util.Dictionary)
 */
public void configure(Element metadata, Dictionary configuration) throws ConfigurationException {
    m_callbacks = new LifecycleCallback[0];
    String imm = metadata.getAttribute("immediate");
    m_immediate = imm != null && imm.equalsIgnoreCase("true");
    PojoMetadata meta = getFactory().getPojoMetadata();
    Element[] hooksMetadata = metadata.getElements("callback");
    for (int i = 0; hooksMetadata != null && i < hooksMetadata.length; i++) {
        String method = hooksMetadata[i].getAttribute("method");
        if (method == null) {
            throw new ConfigurationException("Lifecycle callback : A callback needs to contain a method attribute");
        }
        MethodMetadata met = meta.getMethod(method, new String[0]);
        int transition = -1;
        String trans = hooksMetadata[i].getAttribute("transition");
        if (trans == null) {
            throw new ConfigurationException("Lifecycle callback : the transition attribute is missing");
        } else {
            if (trans.equalsIgnoreCase("validate")) {
                transition = LifecycleCallback.VALIDATE;
            } else if (trans.equalsIgnoreCase("invalidate")) {
                transition = LifecycleCallback.INVALIDATE;
            } else {
                throw new ConfigurationException("Lifecycle callback : Unknown or malformed transition : " + trans);
            }
        }
        LifecycleCallback callback = null;
        if (met == null) {
            callback = new LifecycleCallback(this, transition, method);
        } else {
            callback = new LifecycleCallback(this, transition, met);
        }
        addCallback(callback);
    }
}
Also used : ConfigurationException(org.apache.felix.ipojo.ConfigurationException) Element(org.apache.felix.ipojo.metadata.Element) PojoMetadata(org.apache.felix.ipojo.parser.PojoMetadata) MethodMetadata(org.apache.felix.ipojo.parser.MethodMetadata)

Example 15 with PojoMetadata

use of org.apache.felix.ipojo.parser.PojoMetadata in project felix by apache.

the class ProvidedServiceHandler method initializeComponentFactory.

/**
 * Initialize the component type.
 * @param desc : component type description to populate.
 * @param metadata : component type metadata.
 * @throws ConfigurationException : occurs when the POJO does not implement any interfaces.
 * @see org.apache.felix.ipojo.Handler#initializeComponentFactory(org.apache.felix.ipojo.architecture.ComponentTypeDescription, org.apache.felix.ipojo.metadata.Element)
 */
public void initializeComponentFactory(ComponentTypeDescription desc, Element metadata) throws ConfigurationException {
    // Change ComponentInfo
    Element[] provides = metadata.getElements("provides");
    PojoMetadata manipulation = getFactory().getPojoMetadata();
    for (Element provide : provides) {
        // First : create the serviceSpecification list
        String[] serviceSpecification = manipulation.getInterfaces();
        String parent = manipulation.getSuperClass();
        Set<String> interfaces = new HashSet<String>();
        Set<String> parentClasses = new HashSet<String>();
        try {
            computeInterfacesAndSuperClasses(serviceSpecification, parent, desc.getBundleContext().getBundle(), interfaces, parentClasses);
            getLogger().log(Logger.INFO, "Collected interfaces from " + metadata.getAttribute("classname") + " : " + interfaces);
            getLogger().log(Logger.INFO, "Collected super classes from " + metadata.getAttribute("classname") + " : " + parentClasses);
        } catch (ClassNotFoundException e) {
            throw new ConfigurationException("An interface or parent class cannot be loaded", e);
        }
        String serviceSpecificationStr = provide.getAttribute("specifications");
        if (serviceSpecificationStr == null) {
            serviceSpecificationStr = provide.getAttribute("interface");
            if (serviceSpecificationStr != null) {
                warn("The 'interface' attribute is deprecated, use the 'specifications' attribute instead of 'interface'");
            }
        }
        if (serviceSpecificationStr != null) {
            List<String> itfs = ParseUtils.parseArraysAsList(serviceSpecificationStr);
            for (String itf : itfs) if (!interfaces.contains(itf) && !parentClasses.contains(itf) && !desc.getFactory().getClassName().equals(itf)) {
                desc.getFactory().getLogger().log(Logger.ERROR, "The specification " + itf + " is not implemented by " + metadata.getAttribute("classname"));
            }
            interfaces.clear();
            interfaces.addAll(itfs);
        }
        if (interfaces.isEmpty()) {
            warn("No service interface found in the class hierarchy, use the implementation class");
            interfaces.add(desc.getFactory().getClassName());
        }
        StringBuffer specs = null;
        Set<String> set = new HashSet<String>(interfaces);
        // Remove POJO.
        set.remove(Pojo.class.getName());
        for (String spec : set) {
            desc.addProvidedServiceSpecification(spec);
            if (specs == null) {
                specs = new StringBuffer("{");
                specs.append(spec);
            } else {
                specs.append(',');
                specs.append(spec);
            }
        }
        specs.append('}');
        // Add interface attribute to avoid checking in the configure method
        provide.addAttribute(new Attribute("specifications", specs.toString()));
        Element[] props = provide.getElements("property");
        for (int j = 0; props != null && j < props.length; j++) {
            String name = props[j].getAttribute("name");
            String value = props[j].getAttribute("value");
            String type = props[j].getAttribute("type");
            String field = props[j].getAttribute("field");
            // Get property name :
            if (field != null && name == null) {
                name = field;
            }
            // Check type if not already set
            if (type == null) {
                if (field == null) {
                    throw new ConfigurationException("The property " + name + " has neither type nor field.");
                }
                FieldMetadata fieldMeta = manipulation.getField(field);
                if (fieldMeta == null) {
                    throw new ConfigurationException("A declared property was not found in the implementation class : " + field);
                }
                type = fieldMeta.getFieldType();
                props[j].addAttribute(new Attribute("type", type));
            }
            // Is the property set to immutable
            boolean immutable = false;
            String imm = props[j].getAttribute("immutable");
            if (imm != null && imm.equalsIgnoreCase("true")) {
                immutable = true;
            }
            PropertyDescription pd = new PropertyDescription(name, type, value, immutable);
            desc.addProperty(pd);
            String man = props[j].getAttribute("mandatory");
            if (man != null && man.equalsIgnoreCase("true")) {
                pd.setMandatory();
            }
        }
    }
}
Also used : Pojo(org.apache.felix.ipojo.Pojo) FieldMetadata(org.apache.felix.ipojo.parser.FieldMetadata) Attribute(org.apache.felix.ipojo.metadata.Attribute) Element(org.apache.felix.ipojo.metadata.Element) PropertyDescription(org.apache.felix.ipojo.architecture.PropertyDescription) ConfigurationException(org.apache.felix.ipojo.ConfigurationException) PojoMetadata(org.apache.felix.ipojo.parser.PojoMetadata)

Aggregations

PojoMetadata (org.apache.felix.ipojo.parser.PojoMetadata)15 Element (org.apache.felix.ipojo.metadata.Element)14 ConfigurationException (org.apache.felix.ipojo.ConfigurationException)6 Attribute (org.apache.felix.ipojo.metadata.Attribute)6 MethodMetadata (org.apache.felix.ipojo.parser.MethodMetadata)6 FieldMetadata (org.apache.felix.ipojo.parser.FieldMetadata)5 PropertyDescription (org.apache.felix.ipojo.architecture.PropertyDescription)3 Filter (org.osgi.framework.Filter)2 Event (org.osgi.service.event.Event)2 IOException (java.io.IOException)1 Enumeration (java.util.Enumeration)1 MBeanServer (javax.management.MBeanServer)1 ObjectName (javax.management.ObjectName)1 Pojo (org.apache.felix.ipojo.Pojo)1 Callback (org.apache.felix.ipojo.util.Callback)1 BundleContext (org.osgi.framework.BundleContext)1 InvalidSyntaxException (org.osgi.framework.InvalidSyntaxException)1