Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance. Project price only 1 $
You can buy this project and download/modify it how often you want.
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.camel.blueprint.handler;
import java.io.UnsupportedEncodingException;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.net.URI;
import java.net.URISyntaxException;
import java.net.URL;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.Callable;
import javax.xml.bind.Binder;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.apache.aries.blueprint.BeanProcessor;
import org.apache.aries.blueprint.ComponentDefinitionRegistry;
import org.apache.aries.blueprint.ComponentDefinitionRegistryProcessor;
import org.apache.aries.blueprint.NamespaceHandler;
import org.apache.aries.blueprint.ParserContext;
import org.apache.aries.blueprint.PassThroughMetadata;
import org.apache.aries.blueprint.mutable.MutableBeanMetadata;
import org.apache.aries.blueprint.mutable.MutablePassThroughMetadata;
import org.apache.aries.blueprint.mutable.MutableRefMetadata;
import org.apache.aries.blueprint.mutable.MutableReferenceMetadata;
import org.apache.camel.BeanInject;
import org.apache.camel.CamelContext;
import org.apache.camel.Endpoint;
import org.apache.camel.EndpointInject;
import org.apache.camel.Produce;
import org.apache.camel.PropertyInject;
import org.apache.camel.blueprint.BlueprintCamelContext;
import org.apache.camel.blueprint.BlueprintCamelStateService;
import org.apache.camel.blueprint.BlueprintModelJAXBContextFactory;
import org.apache.camel.blueprint.CamelContextFactoryBean;
import org.apache.camel.blueprint.CamelEndpointFactoryBean;
import org.apache.camel.blueprint.CamelRestContextFactoryBean;
import org.apache.camel.blueprint.CamelRouteContextFactoryBean;
import org.apache.camel.blueprint.CamelRouteTemplateContextFactoryBean;
import org.apache.camel.core.xml.AbstractCamelFactoryBean;
import org.apache.camel.impl.engine.CamelPostProcessorHelper;
import org.apache.camel.impl.engine.DefaultCamelContextNameStrategy;
import org.apache.camel.model.AggregateDefinition;
import org.apache.camel.model.CatchDefinition;
import org.apache.camel.model.DataFormatDefinition;
import org.apache.camel.model.ExpressionNode;
import org.apache.camel.model.ExpressionSubElementDefinition;
import org.apache.camel.model.FromDefinition;
import org.apache.camel.model.MarshalDefinition;
import org.apache.camel.model.Model;
import org.apache.camel.model.OnExceptionDefinition;
import org.apache.camel.model.ProcessorDefinition;
import org.apache.camel.model.ResequenceDefinition;
import org.apache.camel.model.RouteDefinition;
import org.apache.camel.model.SendDefinition;
import org.apache.camel.model.SortDefinition;
import org.apache.camel.model.ToDefinition;
import org.apache.camel.model.ToDynamicDefinition;
import org.apache.camel.model.UnmarshalDefinition;
import org.apache.camel.model.WireTapDefinition;
import org.apache.camel.model.language.ExpressionDefinition;
import org.apache.camel.model.rest.RestBindingMode;
import org.apache.camel.model.rest.RestDefinition;
import org.apache.camel.model.rest.VerbDefinition;
import org.apache.camel.spi.CamelContextNameStrategy;
import org.apache.camel.spi.ComponentResolver;
import org.apache.camel.spi.DataFormatResolver;
import org.apache.camel.spi.LanguageResolver;
import org.apache.camel.spi.NamespaceAware;
import org.apache.camel.spi.PropertiesComponent;
import org.apache.camel.support.ObjectHelper;
import org.apache.camel.support.builder.Namespaces;
import org.apache.camel.support.builder.xml.NamespacesHelper;
import org.apache.camel.support.jsse.KeyStoreParameters;
import org.apache.camel.support.jsse.SSLContextParameters;
import org.apache.camel.support.jsse.SecureRandomParameters;
import org.apache.camel.util.StringHelper;
import org.apache.camel.util.URISupport;
import org.apache.camel.util.blueprint.KeyStoreParametersFactoryBean;
import org.apache.camel.util.blueprint.SSLContextParametersFactoryBean;
import org.apache.camel.util.blueprint.SecureRandomParametersFactoryBean;
import org.osgi.framework.Bundle;
import org.osgi.service.blueprint.container.BlueprintContainer;
import org.osgi.service.blueprint.container.ComponentDefinitionException;
import org.osgi.service.blueprint.reflect.BeanMetadata;
import org.osgi.service.blueprint.reflect.ComponentMetadata;
import org.osgi.service.blueprint.reflect.Metadata;
import org.osgi.service.blueprint.reflect.RefMetadata;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import static org.osgi.service.blueprint.reflect.ComponentMetadata.ACTIVATION_LAZY;
import static org.osgi.service.blueprint.reflect.ServiceReferenceMetadata.AVAILABILITY_MANDATORY;
import static org.osgi.service.blueprint.reflect.ServiceReferenceMetadata.AVAILABILITY_OPTIONAL;
/**
* Camel {@link NamespaceHandler} to parse the Camel related namespaces.
*/
public class CamelNamespaceHandler implements NamespaceHandler {
public static final String BLUEPRINT_NS = "http://camel.apache.org/schema/blueprint";
public static final String SPRING_NS = "http://camel.apache.org/schema/spring";
private static final String CAMEL_CONTEXT = "camelContext";
private static final String ROUTE_CONTEXT = "routeContext";
private static final String ROUTE_TEMPLATE_CONTEXT = "routeTemplateContext";
private static final String REST_CONTEXT = "restContext";
private static final String ENDPOINT = "endpoint";
private static final String KEY_STORE_PARAMETERS = "keyStoreParameters";
private static final String SECURE_RANDOM_PARAMETERS = "secureRandomParameters";
private static final String SSL_CONTEXT_PARAMETERS = "sslContextParameters";
private static final Logger LOG = LoggerFactory.getLogger(CamelNamespaceHandler.class);
private JAXBContext jaxbContext;
/**
* Prepares the nodes before parsing.
*/
public static void doBeforeParse(Node node, String fromNamespace, String toNamespace) {
if (node.getNodeType() == Node.ELEMENT_NODE) {
Document doc = node.getOwnerDocument();
if (node.getNamespaceURI().equals(fromNamespace)) {
doc.renameNode(node, toNamespace, node.getLocalName());
}
// remove whitespace noise from uri, xxxUri attributes, eg new lines, and tabs etc, which allows end users to format
// their Camel routes in more human readable format, but at runtime those attributes must be trimmed
// the parser removes most of the noise, but keeps double spaces in the attribute values
NamedNodeMap map = node.getAttributes();
for (int i = 0; i < map.getLength(); i++) {
Node att = map.item(i);
if (att.getNodeName().equals("uri") || att.getNodeName().endsWith("Uri")) {
final String value = att.getNodeValue();
String before = StringHelper.before(value, "?");
String after = StringHelper.after(value, "?");
if (before != null && after != null) {
// remove all double spaces in the uri parameters
String changed = after.replaceAll("\\s{2,}", "");
if (!after.equals(changed)) {
String newAtr = before.trim() + "?" + changed.trim();
LOG.debug("Removed whitespace noise from attribute {} -> {}", value, newAtr);
att.setNodeValue(newAtr);
}
}
}
}
}
NodeList list = node.getChildNodes();
for (int i = 0; i < list.getLength(); ++i) {
doBeforeParse(list.item(i), fromNamespace, toNamespace);
}
}
@Override
public URL getSchemaLocation(String namespace) {
if (BLUEPRINT_NS.equals(namespace)) {
return getClass().getClassLoader().getResource("camel-blueprint.xsd");
}
return null;
}
@Override
@SuppressWarnings({"rawtypes"})
public Set getManagedClasses() {
return new HashSet<>(Arrays.asList(BlueprintCamelContext.class));
}
@Override
public Metadata parse(Element element, ParserContext context) {
LOG.trace("Parsing element {}", element);
try {
// as the camel-core model namespace is Spring we need to rename from blueprint to spring
doBeforeParse(element, BLUEPRINT_NS, SPRING_NS);
if (element.getLocalName().equals(CAMEL_CONTEXT)) {
return parseCamelContextNode(element, context);
}
if (element.getLocalName().equals(ROUTE_CONTEXT)) {
return parseRouteContextNode(element, context);
}
if (element.getLocalName().equals(ROUTE_TEMPLATE_CONTEXT)) {
return parseRouteContextNode(element, context);
}
if (element.getLocalName().equals(REST_CONTEXT)) {
return parseRestContextNode(element, context);
}
if (element.getLocalName().equals(ENDPOINT)) {
return parseEndpointNode(element, context);
}
if (element.getLocalName().equals(KEY_STORE_PARAMETERS)) {
return parseKeyStoreParametersNode(element, context);
}
if (element.getLocalName().equals(SECURE_RANDOM_PARAMETERS)) {
return parseSecureRandomParametersNode(element, context);
}
if (element.getLocalName().equals(SSL_CONTEXT_PARAMETERS)) {
return parseSSLContextParametersNode(element, context);
}
} finally {
// make sure to rename back so we leave the DOM as-is
doBeforeParse(element, SPRING_NS, BLUEPRINT_NS);
}
return null;
}
private Metadata parseCamelContextNode(Element element, ParserContext context) {
LOG.trace("Parsing CamelContext {}", element);
// Find the id, generate one if needed
String contextId = element.getAttribute("id");
boolean implicitId = false;
// let's avoid folks having to explicitly give an ID to a camel context
if (org.apache.camel.util.ObjectHelper.isEmpty(contextId)) {
// if no explicit id was set then use a default auto generated name
CamelContextNameStrategy strategy = new DefaultCamelContextNameStrategy();
contextId = strategy.getName();
element.setAttributeNS(null, "id", contextId);
implicitId = true;
}
// now let's parse the routes with JAXB
Binder binder;
try {
binder = getJaxbContext().createBinder();
} catch (JAXBException e) {
throw new ComponentDefinitionException("Failed to create the JAXB binder : " + e, e);
}
Object value = parseUsingJaxb(element, context, binder);
if (!(value instanceof CamelContextFactoryBean)) {
throw new ComponentDefinitionException("Expected an instance of " + CamelContextFactoryBean.class);
}
CamelContextFactoryBean ccfb = (CamelContextFactoryBean) value;
ccfb.setImplicitId(implicitId);
MutablePassThroughMetadata factory = context.createMetadata(MutablePassThroughMetadata.class);
factory.setId(".camelBlueprint.passThrough." + contextId);
factory.setObject(new PassThroughCallable<>(value));
MutableBeanMetadata factory2 = context.createMetadata(MutableBeanMetadata.class);
factory2.setId(".camelBlueprint.factory." + contextId);
factory2.setFactoryComponent(factory);
factory2.setFactoryMethod("call");
factory2.setInitMethod("afterPropertiesSet");
factory2.setDestroyMethod("destroy");
factory2.addProperty("blueprintContainer", createRef(context, "blueprintContainer"));
factory2.addProperty("bundleContext", createRef(context, "blueprintBundleContext"));
// We need to add other components which the camel context dependsOn
if (org.apache.camel.util.ObjectHelper.isNotEmpty(ccfb.getDependsOn())) {
factory2.setDependsOn(Arrays.asList(ccfb.getDependsOn().split(" |,")));
}
context.getComponentDefinitionRegistry().registerComponentDefinition(factory2);
MutableBeanMetadata ctx = context.createMetadata(MutableBeanMetadata.class);
ctx.setId(contextId);
ctx.setRuntimeClass(BlueprintCamelContext.class);
ctx.setFactoryComponent(factory2);
ctx.setFactoryMethod("getContext");
ctx.addProperty("bundleStateService", createRef(context, ".camelBlueprint.bundleStateService"));
ctx.setInitMethod("build");
ctx.setDestroyMethod("destroy");
// Register factory beans
registerBeans(context, contextId, ccfb.getThreadPools());
registerBeans(context, contextId, ccfb.getEndpoints());
registerBeans(context, contextId, ccfb.getRedeliveryPolicies());
registerBeans(context, contextId, ccfb.getBeansFactory());
// Register single CamelBundleStateService - shared for all bundles and all Blueprint Camel contexts
registerBundleStateService(context);
// Register processors
MutablePassThroughMetadata beanProcessorFactory = context.createMetadata(MutablePassThroughMetadata.class);
beanProcessorFactory.setId(".camelBlueprint.processor.bean.passThrough." + contextId);
beanProcessorFactory.setObject(new PassThroughCallable