This is an automated email from the ASF dual-hosted git repository.

davsclaus pushed a commit to branch properties
in repository https://gitbox.apache.org/repos/asf/camel.git

commit 1794a610f5a503d04696b3c5878313be8960b2ce
Author: Claus Ibsen <claus.ib...@gmail.com>
AuthorDate: Wed Jul 3 11:50:27 2019 +0200

    CAMEL-13708: Properties component should have API to make it easier to 
lookup a property on-demand or from all pre-loaded properties.
---
 .../config/CamelMicroProfilePropertiesSource.java  |   2 +
 .../src/main/docs/properties-component.adoc        |   2 +-
 .../properties/ClasspathPropertiesSource.java      |  70 +++++++++++++
 .../properties/DefaultPropertiesResolver.java      |   1 +
 .../component/properties/FilePropertiesSource.java |  70 +++++++++++++
 .../properties/LocationPropertiesSource.java       |  22 ++++
 .../LocationPropertiesSourceSupport.java           | 114 +++++++++++++++++++++
 .../component/properties/PropertiesComponent.java  | 106 ++++++++++++++-----
 .../component/properties/PropertiesLocation.java   |   2 +-
 .../component/properties/RefPropertiesSource.java  |  54 ++++++++++
 .../properties/PropertiesComponentRestartTest.java |  67 ------------
 .../properties/PropertiesResolverTest.java         |  73 -------------
 .../issues/PropertiesAvailableEverywhereTest.java  |  14 +--
 .../PropertiesComponentConfiguration.java          |   5 +
 14 files changed, 422 insertions(+), 180 deletions(-)

diff --git 
a/components/camel-microprofile-config/src/main/java/org/apache/camel/component/microprofile/config/CamelMicroProfilePropertiesSource.java
 
b/components/camel-microprofile-config/src/main/java/org/apache/camel/component/microprofile/config/CamelMicroProfilePropertiesSource.java
index 7622889..ce9ca88 100644
--- 
a/components/camel-microprofile-config/src/main/java/org/apache/camel/component/microprofile/config/CamelMicroProfilePropertiesSource.java
+++ 
b/components/camel-microprofile-config/src/main/java/org/apache/camel/component/microprofile/config/CamelMicroProfilePropertiesSource.java
@@ -33,6 +33,8 @@ import org.slf4j.LoggerFactory;
  */
 public class CamelMicroProfilePropertiesSource extends ServiceSupport 
implements LoadablePropertiesSource {
 
+    // TODO: Should not be loadable but regular source so we lookup on demand
+
     private static final Logger LOG = 
LoggerFactory.getLogger(CamelMicroProfilePropertiesSource.class);
 
     private final Properties properties = new OrderedProperties();
diff --git 
a/components/camel-properties/src/main/docs/properties-component.adoc 
b/components/camel-properties/src/main/docs/properties-component.adoc
index da6bce5..8e784be 100644
--- a/components/camel-properties/src/main/docs/properties-component.adoc
+++ b/components/camel-properties/src/main/docs/properties-component.adoc
@@ -25,7 +25,7 @@ The Properties component supports 16 options, which are 
listed below.
 | *locations* (common) | A list of locations to load properties. This option 
will override any default locations and only use the locations from this 
option. |  | List
 | *location* (common) | A list of locations to load properties. You can use 
comma to separate multiple locations. This option will override any default 
locations and only use the locations from this option. |  | String
 | *encoding* (common) | Encoding to use when loading properties file from the 
file system or classpath. If no encoding has been set, then the properties 
files is loaded using ISO-8859-1 encoding (latin-1) as documented by 
java.util.Properties#load(java.io.InputStream) |  | String
-| *propertiesResolver* (common) | To use a custom PropertiesResolver |  | 
PropertiesResolver
+| *propertiesResolver* (common) | *Deprecated* To use a custom 
PropertiesResolver |  | PropertiesResolver
 | *propertiesParser* (common) | To use a custom PropertiesParser |  | 
PropertiesParser
 | *cache* (common) | Whether or not to cache loaded properties. The default 
value is true. | true | boolean
 | *defaultFallbackEnabled* (common) | If false, the component does not attempt 
to find a default for the key by looking after the colon separator. | true | 
boolean
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/ClasspathPropertiesSource.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/ClasspathPropertiesSource.java
new file mode 100644
index 0000000..a69e836
--- /dev/null
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/ClasspathPropertiesSource.java
@@ -0,0 +1,70 @@
+/**
+ * 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
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * 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.component.properties;
+
+import java.io.BufferedReader;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.util.Properties;
+
+import org.apache.camel.RuntimeCamelException;
+import org.apache.camel.util.IOHelper;
+import org.apache.camel.util.OrderedProperties;
+
+public class ClasspathPropertiesSource extends LocationPropertiesSourceSupport 
{
+
+    public ClasspathPropertiesSource(PropertiesComponent propertiesComponent, 
PropertiesLocation location, boolean ignoreMissingLocation) {
+        super(propertiesComponent, location, ignoreMissingLocation);
+    }
+
+    @Override
+    public String getName() {
+        return "ClasspathPropertiesSource[" + getLocation().getPath() + "]";
+    }
+
+    @Override
+    protected Properties loadPropertiesFromLocation(PropertiesComponent 
propertiesComponent, boolean ignoreMissingLocation, PropertiesLocation 
location) {
+        Properties answer = new OrderedProperties();
+        String path = location.getPath();
+
+        InputStream is = 
propertiesComponent.getCamelContext().getClassResolver().loadResourceAsStream(path);
+        Reader reader = null;
+        if (is == null) {
+            if (!ignoreMissingLocation && !location.isOptional()) {
+                throw RuntimeCamelException.wrapRuntimeCamelException(new 
FileNotFoundException("Properties file " + path + " not found in classpath"));
+            }
+        } else {
+            try {
+                if (propertiesComponent.getEncoding() != null) {
+                    reader = new BufferedReader(new InputStreamReader(is, 
propertiesComponent.getEncoding()));
+                    answer.load(reader);
+                } else {
+                    answer.load(is);
+                }
+            } catch (IOException e) {
+                throw RuntimeCamelException.wrapRuntimeCamelException(e);
+            } finally {
+                IOHelper.close(reader, is);
+            }
+        }
+        return answer;
+    }
+
+}
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/DefaultPropertiesResolver.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/DefaultPropertiesResolver.java
index 1e164ff..a88c587 100644
--- 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/DefaultPropertiesResolver.java
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/DefaultPropertiesResolver.java
@@ -39,6 +39,7 @@ import org.apache.camel.util.OrderedProperties;
  * You can denote <tt>classpath:</tt> or <tt>file:</tt> as prefix in the uri 
to select whether the file
  * is located in the classpath or on the file system.
  */
+@Deprecated
 public class DefaultPropertiesResolver implements PropertiesResolver {
 
     private final PropertiesComponent propertiesComponent;
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/FilePropertiesSource.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/FilePropertiesSource.java
new file mode 100644
index 0000000..3ac9810
--- /dev/null
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/FilePropertiesSource.java
@@ -0,0 +1,70 @@
+/**
+ * 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
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * 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.component.properties;
+
+import java.io.BufferedReader;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.util.Properties;
+
+import org.apache.camel.RuntimeCamelException;
+import org.apache.camel.util.IOHelper;
+import org.apache.camel.util.OrderedProperties;
+
+public class FilePropertiesSource extends LocationPropertiesSourceSupport {
+
+    protected FilePropertiesSource(PropertiesComponent propertiesComponent, 
PropertiesLocation location, boolean ignoreMissingLocation) {
+        super(propertiesComponent, location, ignoreMissingLocation);
+    }
+
+    @Override
+    public String getName() {
+        return "FilePropertiesSource[" + getLocation().getPath() + "]";
+    }
+
+    protected Properties loadPropertiesFromLocation(PropertiesComponent 
propertiesComponent, boolean ignoreMissingLocation, PropertiesLocation 
location) {
+        Properties answer = new OrderedProperties();
+        String path = location.getPath();
+
+        InputStream is = null;
+        Reader reader = null;
+        try {
+            is = new FileInputStream(path);
+            if (propertiesComponent.getEncoding() != null) {
+                reader = new BufferedReader(new InputStreamReader(is, 
propertiesComponent.getEncoding()));
+                answer.load(reader);
+            } else {
+                answer.load(is);
+            }
+        } catch (FileNotFoundException e) {
+            if (!ignoreMissingLocation && !location.isOptional()) {
+                throw RuntimeCamelException.wrapRuntimeCamelException(e);
+            }
+        } catch (IOException e) {
+            throw RuntimeCamelException.wrapRuntimeCamelException(e);
+        } finally {
+            IOHelper.close(reader, is);
+        }
+
+        return answer;
+    }
+
+}
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/LocationPropertiesSource.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/LocationPropertiesSource.java
new file mode 100644
index 0000000..4fbf5ca
--- /dev/null
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/LocationPropertiesSource.java
@@ -0,0 +1,22 @@
+/**
+ * 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
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * 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.component.properties;
+
+public interface LocationPropertiesSource extends PropertiesSource {
+
+    PropertiesLocation getLocation();
+}
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/LocationPropertiesSourceSupport.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/LocationPropertiesSourceSupport.java
new file mode 100644
index 0000000..73bd40a
--- /dev/null
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/LocationPropertiesSourceSupport.java
@@ -0,0 +1,114 @@
+/**
+ * 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
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * 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.component.properties;
+
+import java.util.Map;
+import java.util.Properties;
+
+import org.apache.camel.support.service.ServiceSupport;
+import org.apache.camel.util.OrderedProperties;
+
+public abstract class LocationPropertiesSourceSupport extends ServiceSupport 
implements LoadablePropertiesSource, LocationPropertiesSource {
+
+    private final Properties properties = new OrderedProperties();
+    private final PropertiesComponent propertiesComponent;
+    private final PropertiesLocation location;
+    private final boolean ignoreMissingLocation;
+
+    protected LocationPropertiesSourceSupport(PropertiesComponent 
propertiesComponent, PropertiesLocation location, boolean 
ignoreMissingLocation) {
+        this.propertiesComponent = propertiesComponent;
+        this.location = location;
+        this.ignoreMissingLocation = ignoreMissingLocation;
+    }
+
+    abstract Properties loadPropertiesFromLocation(PropertiesComponent 
propertiesComponent, boolean ignoreMissingLocation, PropertiesLocation 
location);
+
+    public PropertiesLocation getLocation() {
+        return location;
+    }
+
+    @Override
+    public Properties loadProperties() {
+        return properties;
+    }
+
+    @Override
+    public String getProperty(String name) {
+        return properties.getProperty(name);
+    }
+
+    @Override
+    protected void doInit() throws Exception {
+        super.doInit();
+
+        Properties prop = loadPropertiesFromLocation(propertiesComponent, 
ignoreMissingLocation, location);
+        prop = prepareLoadedProperties(prop);
+        properties.putAll(prop);
+    }
+
+    @Override
+    protected void doStart() throws Exception {
+        // noop
+    }
+
+    @Override
+    protected void doStop() throws Exception {
+        // noop
+    }
+
+    /**
+     * Strategy to prepare loaded properties before being used by Camel.
+     * <p/>
+     * This implementation will ensure values are trimmed, as loading 
properties from
+     * a file with values having trailing spaces is not automatic trimmed by 
the Properties API
+     * from the JDK.
+     *
+     * @param properties  the properties
+     * @return the prepared properties
+     */
+    protected static Properties prepareLoadedProperties(Properties properties) 
{
+        Properties answer = new OrderedProperties();
+        for (Map.Entry<Object, Object> entry : properties.entrySet()) {
+            Object key = entry.getKey();
+            Object value = entry.getValue();
+            if (value instanceof String) {
+                String s = (String) value;
+
+                // trim any trailing spaces which can be a problem when 
loading from
+                // a properties file, note that java.util.Properties does 
already this
+                // for any potential leading spaces so there's nothing to do 
there
+                value = trimTrailingWhitespaces(s);
+            }
+            answer.put(key, value);
+        }
+        return answer;
+    }
+
+    private static String trimTrailingWhitespaces(String s) {
+        int endIndex = s.length();
+        for (int index = s.length() - 1; index >= 0; index--) {
+            if (s.charAt(index) == ' ') {
+                endIndex = index;
+            } else {
+                break;
+            }
+        }
+        String answer = s.substring(0, endIndex);
+        return answer;
+    }
+
+}
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java
index f6dde5d..1e109c6 100644
--- 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesComponent.java
@@ -100,7 +100,7 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
 
     private static final Logger LOG = 
LoggerFactory.getLogger(PropertiesComponent.class);
 
-    @SuppressWarnings("unchecked")
+    // TODO: Get rid of cacheMap
     private final Map<CacheKey, Properties> cacheMap = 
LRUCacheFactory.newLRUSoftCache(1000);
     private transient Properties cachedLoadedProperties;
     private final Map<String, PropertiesFunction> functions = new 
LinkedHashMap<>();
@@ -108,6 +108,7 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
     private PropertiesParser propertiesParser = new 
DefaultPropertiesParser(this);
     private List<PropertiesLocation> locations = Collections.emptyList();
     private final List<PropertiesSource> sources = new ArrayList<>();
+    private final List<LocationPropertiesSource> locationSources = new 
ArrayList<>();
 
     @Metadata
     private boolean ignoreMissingLocation;
@@ -178,12 +179,18 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
 
     public String parseUri(String uri) {
         // optimise to only load properties once as we use the configured 
locations
-        if (cache && cachedLoadedProperties == null) {
-            cachedLoadedProperties = doLoadProperties(locations);
+        if (cache) {
+            if (cachedLoadedProperties == null) {
+                cachedLoadedProperties = doLoadProperties(null);
+            }
+            return parseUri(uri, cachedLoadedProperties);
+        } else {
+            Properties prop = doLoadProperties(null);
+            return parseUri(uri, prop);
         }
-        return cachedLoadedProperties != null ? parseUri(uri, 
cachedLoadedProperties) : parseUri(uri, doLoadProperties(locations));
     }
 
+    @Deprecated
     public String parseUri(String uri, String... locations) {
         return parseUri(
             uri,
@@ -193,20 +200,26 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
     }
 
     public Properties loadProperties() {
-        if (cache && cachedLoadedProperties == null) {
-            cachedLoadedProperties = doLoadProperties(locations);
+        if (cache) {
+            if (cachedLoadedProperties == null) {
+                cachedLoadedProperties = doLoadProperties(null);
+            }
+            return cachedLoadedProperties;
+        } else {
+            return doLoadProperties(null);
         }
-        return cachedLoadedProperties != null ? cachedLoadedProperties : 
doLoadProperties(locations);
     }
 
+    @Deprecated
     public Properties loadProperties(String... locations) {
         if (locations != null) {
             return 
doLoadProperties(Arrays.stream(locations).map(PropertiesLocation::new).collect(Collectors.toList()));
+        } else {
+            return new OrderedProperties();
         }
-        return new OrderedProperties();
     }
 
-    protected Properties doLoadProperties(List<PropertiesLocation> paths) {
+    protected Properties doLoadProperties(List<PropertiesLocation> 
extraLocations) {
         Properties prop = new OrderedProperties();
 
         // use initial properties
@@ -214,22 +227,11 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
             prop.putAll(initialProperties);
         }
 
-        // add 3rd party sources
-        if (!sources.isEmpty()) {
-            for (PropertiesSource ps : sources) {
-                if (ps instanceof LoadablePropertiesSource) {
-                    LoadablePropertiesSource lps = (LoadablePropertiesSource) 
ps;
-                    Properties p = lps.loadProperties();
-                    prop.putAll(p);
-                }
-            }
-        }
-
-        // use locations
-        if (paths != null) {
+        // use the old way with locations
+        if (extraLocations != null) {
             // location may contain JVM system property or OS environment 
variables
             // so we need to parse those
-            List<PropertiesLocation> locations = parseLocations(paths);
+            List<PropertiesLocation> locations = 
parseLocations(extraLocations);
 
             // check cache first
             CacheKey key = new CacheKey(locations);
@@ -241,6 +243,26 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
                 }
             }
             prop.putAll(locationsProp);
+        } else {
+            // else use the new way with property sources
+            if (!locationSources.isEmpty()) {
+                for (PropertiesSource ps : locationSources) {
+                    if (ps instanceof LoadablePropertiesSource) {
+                        LoadablePropertiesSource lps = 
(LoadablePropertiesSource) ps;
+                        Properties p = lps.loadProperties();
+                        prop.putAll(p);
+                    }
+                }
+            }
+            if (!sources.isEmpty()) {
+                for (PropertiesSource ps : sources) {
+                    if (ps instanceof LoadablePropertiesSource) {
+                        LoadablePropertiesSource lps = 
(LoadablePropertiesSource) ps;
+                        Properties p = lps.loadProperties();
+                        prop.putAll(p);
+                    }
+                }
+            }
         }
 
         // use override properties
@@ -274,6 +296,9 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
         return propertiesParser.parseUri(uri, properties, prefixToken, 
suffixToken, defaultFallbackEnabled);
     }
 
+    /**
+     * Gets the configured locations
+     */
     public List<PropertiesLocation> getLocations() {
         return locations;
     }
@@ -283,7 +308,15 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
      * This option will override any default locations and only use the 
locations from this option.
      */
     public void setLocations(List<PropertiesLocation> locations) {
+        // reset locations
+        locations = parseLocations(locations);
         this.locations = Collections.unmodifiableList(locations);
+
+        // we need to reset them as sources as well
+        this.locationSources.clear();
+        for (PropertiesLocation loc : locations) {
+            addPropertiesLocationsAsPropertiesSource(loc);
+        }
     }
 
     /**
@@ -355,6 +388,7 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
         this.encoding = encoding;
     }
 
+    @Deprecated
     public PropertiesResolver getPropertiesResolver() {
         return propertiesResolver;
     }
@@ -362,6 +396,7 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
     /**
      * To use a custom PropertiesResolver
      */
+    @Deprecated
     public void setPropertiesResolver(PropertiesResolver propertiesResolver) {
         this.propertiesResolver = propertiesResolver;
     }
@@ -548,12 +583,14 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
      * Adds a custom {@link PropertiesSource}
      */
     public void addPropertiesSource(PropertiesSource propertiesSource) {
-        // prepare properties sources which we must do eager
         if (propertiesSource instanceof CamelContextAware) {
             ((CamelContextAware) 
propertiesSource).setCamelContext(getCamelContext());
         }
-        ServiceHelper.initService(propertiesSource);
-        sources.add(propertiesSource);
+        if (propertiesSource instanceof LocationPropertiesSource) {
+            locationSources.add((LocationPropertiesSource) propertiesSource);
+        } else {
+            sources.add(propertiesSource);
+        }
     }
 
     @Override
@@ -586,8 +623,9 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
         super.doStart();
 
         // sort the sources
+        locationSources.sort(OrderedComparator.get());
         sources.sort(OrderedComparator.get());
-        ServiceHelper.startService(sources);
+        ServiceHelper.startService(locationSources, sources);
 
         if (systemPropertiesMode != SYSTEM_PROPERTIES_MODE_NEVER
                 && systemPropertiesMode != SYSTEM_PROPERTIES_MODE_FALLBACK
@@ -610,10 +648,22 @@ public class PropertiesComponent extends DefaultComponent 
implements org.apache.
     protected void doStop() throws Exception {
         cacheMap.clear();
         cachedLoadedProperties = null;
-        ServiceHelper.stopAndShutdownService(sources);
+        ServiceHelper.stopAndShutdownServices(locationSources, sources);
         super.doStop();
     }
 
+    private void addPropertiesLocationsAsPropertiesSource(PropertiesLocation 
location) {
+        if ("ref".equals(location.getResolver())) {
+            addPropertiesSource(new RefPropertiesSource(this, location, 
ignoreMissingLocation));
+        } else if ("file".equals(location.getResolver())) {
+            addPropertiesSource(new FilePropertiesSource(this, location, 
ignoreMissingLocation));
+        } else if ("classpath".equals(location.getResolver())) {
+            addPropertiesSource(new ClasspathPropertiesSource(this, location, 
ignoreMissingLocation));
+        } else {
+            // classpath is also default
+            addPropertiesSource(new ClasspathPropertiesSource(this, location, 
ignoreMissingLocation));
+        }
+    }
     private List<PropertiesLocation> parseLocations(List<PropertiesLocation> 
locations) {
         List<PropertiesLocation> answer = new ArrayList<>();
 
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesLocation.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesLocation.java
index 888438b..9902ebb 100644
--- 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesLocation.java
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/PropertiesLocation.java
@@ -18,7 +18,7 @@ package org.apache.camel.component.properties;
 
 import org.apache.camel.util.StringHelper;
 
-public class PropertiesLocation {
+public final class PropertiesLocation {
     private final String resolver;
     private final String path;
     private final boolean optional;
diff --git 
a/components/camel-properties/src/main/java/org/apache/camel/component/properties/RefPropertiesSource.java
 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/RefPropertiesSource.java
new file mode 100644
index 0000000..1c9511a
--- /dev/null
+++ 
b/components/camel-properties/src/main/java/org/apache/camel/component/properties/RefPropertiesSource.java
@@ -0,0 +1,54 @@
+/**
+ * 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
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * 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.component.properties;
+
+import java.io.FileNotFoundException;
+import java.util.Map;
+import java.util.Properties;
+
+import org.apache.camel.RuntimeCamelException;
+import org.apache.camel.util.OrderedProperties;
+
+public class RefPropertiesSource extends LocationPropertiesSourceSupport  {
+
+    public RefPropertiesSource(PropertiesComponent propertiesComponent, 
PropertiesLocation location, boolean ignoreMissingLocation) {
+        super(propertiesComponent, location, ignoreMissingLocation);
+    }
+
+    @Override
+    public String getName() {
+        return "RefPropertiesSource[" + getLocation().getPath() + "]";
+    }
+
+    protected Properties loadPropertiesFromLocation(PropertiesComponent 
propertiesComponent, boolean ignoreMissingLocation, PropertiesLocation 
location) {
+        String path = location.getPath();
+        Properties answer;
+        try {
+            answer = 
propertiesComponent.getCamelContext().getRegistry().lookupByNameAndType(path, 
Properties.class);
+        } catch (Exception ex) {
+            // just look up the Map as a fault back
+            Map map = 
propertiesComponent.getCamelContext().getRegistry().lookupByNameAndType(path, 
Map.class);
+            answer = new OrderedProperties();
+            answer.putAll(map);
+        }
+        if (answer == null && (!ignoreMissingLocation && 
!location.isOptional())) {
+            throw RuntimeCamelException.wrapRuntimeCamelException(new 
FileNotFoundException("Properties " + path + " not found in registry"));
+        }
+        return answer != null ? answer : new OrderedProperties();
+    }
+
+}
diff --git 
a/core/camel-core/src/test/java/org/apache/camel/component/properties/PropertiesComponentRestartTest.java
 
b/core/camel-core/src/test/java/org/apache/camel/component/properties/PropertiesComponentRestartTest.java
deleted file mode 100644
index 1f398d5..0000000
--- 
a/core/camel-core/src/test/java/org/apache/camel/component/properties/PropertiesComponentRestartTest.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * 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.component.properties;
-
-import java.util.List;
-import java.util.Properties;
-
-import org.apache.camel.CamelContext;
-import org.apache.camel.ContextTestSupport;
-import org.apache.camel.impl.DefaultCamelContext;
-import org.junit.Test;
-
-public class PropertiesComponentRestartTest extends ContextTestSupport {
-
-    private int resolvedCount;
-
-    @Test
-    public void testPropertiesComponentCacheClearedOnStop() throws Exception {
-
-        context.start();
-
-        context.resolvePropertyPlaceholders("{{cool.end}}");
-        context.resolvePropertyPlaceholders("{{cool.end}}");
-        context.resolvePropertyPlaceholders("{{cool.end}}");
-        assertEquals(1, resolvedCount); // one cache miss
-
-        context.stop();
-        context.start();
-
-        context.resolvePropertyPlaceholders("{{cool.end}}");
-        context.resolvePropertyPlaceholders("{{cool.end}}");
-        context.resolvePropertyPlaceholders("{{cool.end}}");
-        assertEquals(2, resolvedCount); // one more cache miss -- stop() 
cleared the cache
-    }
-
-    @Override
-    protected CamelContext createCamelContext() throws Exception {
-        final PropertiesComponent pc = new 
PropertiesComponent("classpath:org/apache/camel/component/properties/myproperties.properties");
-        pc.setPropertiesResolver(new PropertiesResolver() {
-            public Properties resolveProperties(CamelContext context, boolean 
ignoreMissingLocation, List<PropertiesLocation> locations) {
-                resolvedCount++;
-                return new 
DefaultPropertiesResolver(pc).resolveProperties(context, ignoreMissingLocation, 
locations);
-            }
-        });
-
-        // put the properties component into the registry so that it survives 
restarts
-
-        CamelContext context = new DefaultCamelContext();
-        context.getRegistry().bind("properties", pc);
-        return context;
-    }
-
-}
diff --git 
a/core/camel-core/src/test/java/org/apache/camel/component/properties/PropertiesResolverTest.java
 
b/core/camel-core/src/test/java/org/apache/camel/component/properties/PropertiesResolverTest.java
deleted file mode 100644
index a71db59..0000000
--- 
a/core/camel-core/src/test/java/org/apache/camel/component/properties/PropertiesResolverTest.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/*
- * 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.component.properties;
-
-import java.util.List;
-import java.util.Properties;
-
-import org.apache.camel.CamelContext;
-import org.apache.camel.ContextTestSupport;
-import org.apache.camel.builder.RouteBuilder;
-import org.junit.Test;
-
-public class PropertiesResolverTest extends ContextTestSupport {
-
-    @Test
-    public void testPropertiesResolver() throws Exception {
-        getMockEndpoint("mock:result").expectedMessageCount(1);
-
-        template.sendBody("direct:start", "Hello World");
-
-        assertMockEndpointsSatisfied();
-    }
-
-    @Override
-    protected RouteBuilder createRouteBuilder() throws Exception {
-        return new RouteBuilder() {
-            @Override
-            public void configure() throws Exception {
-                context.addRoutes(new RouteBuilder() {
-                    @Override
-                    public void configure() throws Exception {
-                        from("direct:start").to("properties:foo");
-                    }
-                });
-            }
-        };
-    }
-
-    protected CamelContext createCamelContext() throws Exception {
-        CamelContext context = super.createCamelContext();
-
-        PropertiesComponent pc = new PropertiesComponent();
-        pc.setLocation("foo");
-        pc.setPropertiesResolver(new MyCustomResolver());
-        context.addComponent("properties", pc);
-
-        return context;
-    }
-
-    public static class MyCustomResolver implements PropertiesResolver {
-
-        public Properties resolveProperties(CamelContext context, boolean 
ignoreMissingLocation, List<PropertiesLocation> locations) {
-            Properties answer = new Properties();
-            answer.put("foo", "mock:result");
-            return answer;
-        }
-    }
-
-}
\ No newline at end of file
diff --git 
a/core/camel-core/src/test/java/org/apache/camel/issues/PropertiesAvailableEverywhereTest.java
 
b/core/camel-core/src/test/java/org/apache/camel/issues/PropertiesAvailableEverywhereTest.java
index 8840784..7413799 100644
--- 
a/core/camel-core/src/test/java/org/apache/camel/issues/PropertiesAvailableEverywhereTest.java
+++ 
b/core/camel-core/src/test/java/org/apache/camel/issues/PropertiesAvailableEverywhereTest.java
@@ -16,15 +16,12 @@
  */
 package org.apache.camel.issues;
 
-import java.util.List;
 import java.util.Properties;
 
 import org.apache.camel.CamelContext;
 import org.apache.camel.ContextTestSupport;
 import org.apache.camel.builder.RouteBuilder;
 import org.apache.camel.component.properties.PropertiesComponent;
-import org.apache.camel.component.properties.PropertiesLocation;
-import org.apache.camel.component.properties.PropertiesResolver;
 import org.junit.Test;
 
 public class PropertiesAvailableEverywhereTest extends ContextTestSupport {
@@ -35,14 +32,11 @@ public class PropertiesAvailableEverywhereTest extends 
ContextTestSupport {
 
         final Properties properties = new Properties();
         properties.put("foo", "bar");
+
+        camelContext.getRegistry().bind("myProp", properties);
+
         PropertiesComponent pc = camelContext.getComponent("properties", 
PropertiesComponent.class);
-        pc.setLocations(new String[0]);
-        pc.setPropertiesResolver(new PropertiesResolver() {
-            @Override
-            public Properties resolveProperties(CamelContext context, boolean 
ignoreMissingLocation, List<PropertiesLocation> locations) {
-                return properties;
-            }
-        });
+        pc.addLocation("ref:myProp");
 
         return camelContext;
     }
diff --git 
a/platforms/spring-boot/components-starter/camel-properties-starter/src/main/java/org/apache/camel/component/properties/springboot/PropertiesComponentConfiguration.java
 
b/platforms/spring-boot/components-starter/camel-properties-starter/src/main/java/org/apache/camel/component/properties/springboot/PropertiesComponentConfiguration.java
index 3d81f6c..7bda5fc 100644
--- 
a/platforms/spring-boot/components-starter/camel-properties-starter/src/main/java/org/apache/camel/component/properties/springboot/PropertiesComponentConfiguration.java
+++ 
b/platforms/spring-boot/components-starter/camel-properties-starter/src/main/java/org/apache/camel/component/properties/springboot/PropertiesComponentConfiguration.java
@@ -21,6 +21,7 @@ import javax.annotation.Generated;
 import org.apache.camel.component.properties.PropertiesLocation;
 import org.apache.camel.spring.boot.ComponentConfigurationPropertiesCommon;
 import org.springframework.boot.context.properties.ConfigurationProperties;
+import 
org.springframework.boot.context.properties.DeprecatedConfigurationProperty;
 
 /**
  * The properties component is used for using property placeholders in endpoint
@@ -61,6 +62,7 @@ public class PropertiesComponentConfiguration
      * To use a custom PropertiesResolver. The option is a
      * org.apache.camel.component.properties.PropertiesResolver type.
      */
+    @Deprecated
     private String propertiesResolver;
     /**
      * To use a custom PropertiesParser. The option is a
@@ -151,10 +153,13 @@ public class PropertiesComponentConfiguration
         this.encoding = encoding;
     }
 
+    @Deprecated
+    @DeprecatedConfigurationProperty
     public String getPropertiesResolver() {
         return propertiesResolver;
     }
 
+    @Deprecated
     public void setPropertiesResolver(String propertiesResolver) {
         this.propertiesResolver = propertiesResolver;
     }

Reply via email to