You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by ni...@apache.org on 2013/09/01 09:48:18 UTC

[1/4] CAMEL-6676 Added camel-facebook component with thanks for Dhiraj

Updated Branches:
  refs/heads/master 81377b0f8 -> 124c0e344


http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java
new file mode 100644
index 0000000..0cdc15f
--- /dev/null
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java
@@ -0,0 +1,132 @@
+package org.apache.camel.component.facebook.data;
+
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.util.*;
+import org.apache.camel.component.facebook.config.FacebookEndpointConfiguration;
+import org.junit.Test;
+
+import facebook4j.Facebook;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+
+/**
+ * Test {@link FacebookMethodsTypeHelper}.
+ */
+public class FacebookMethodsTypeHelperTest {
+
+    private Set<String> names = new HashSet<String>();
+    private final List<String> getExcludes;
+    private final List<String> searchIncludes;
+
+    public FacebookMethodsTypeHelperTest() {
+        // get all method names
+        for (Class<?> aClass : Facebook.class.getInterfaces()) {
+            if (aClass.getName().endsWith("Methods")) {
+                for (Method method : aClass.getDeclaredMethods()) {
+                    names.add(getShortName(method.getName()));
+                }
+            }
+        }
+
+        getExcludes = Arrays.asList("places");
+        searchIncludes = Arrays.asList("checkins", "events", "groups", "locations", "places", "posts", "users");
+    }
+
+    private String getShortName(String name) {
+        if (name.startsWith("get")) {
+            name = Character.toLowerCase(name.charAt(3)) + name.substring(4);
+        } else if (name.startsWith("search") && !"search".equals(name)) {
+            name = Character.toLowerCase(name.charAt(6)) + name.substring(7);
+        }
+        return name;
+    }
+
+    @Test
+    public void testGetCandidateMethods() throws Exception {
+        for (FacebookMethodsType method : FacebookMethodsType.values()) {
+            final String name = method.getName();
+            final String shortName = getShortName(method.getName());
+
+            final String[] argNames = method.getArgNames().toArray(new String[method.getArgNames().size()]);
+            List<FacebookMethodsType> candidates = FacebookMethodsTypeHelper.getCandidateMethods(name, argNames);
+            assertFalse("No candidate methods for " + name, candidates.isEmpty());
+
+            if (!name.equals(shortName) && !"search".equals(name)) {
+                if (!getExcludes.contains(shortName)) {
+                    candidates = FacebookMethodsTypeHelper.getCandidateMethods(
+                        FacebookMethodsTypeHelper.convertToGetMethod(shortName), new String[0]);
+                    assertFalse("No candidate get methods for " + shortName, candidates.isEmpty());
+                }
+
+                if (searchIncludes.contains(shortName)) {
+                    candidates = FacebookMethodsTypeHelper.getCandidateMethods(
+                        FacebookMethodsTypeHelper.convertToSearchMethod(shortName), new String[0]);
+                    assertFalse("No candidate search methods for " + shortName, candidates.isEmpty());
+                }
+            }
+        }
+    }
+
+    @Test
+    public void testFilterMethods() throws Exception {
+        // TODO
+    }
+
+    @Test
+    public void testGetArguments() throws Exception {
+        final Class<?>[] interfaces = Facebook.class.getInterfaces();
+        for (Class clazz : interfaces) {
+            if (clazz.getName().endsWith("Methods")) {
+                // check all methods of this *Methods interface
+                for (Method method : clazz.getDeclaredMethods()) {
+                    // will throw an exception if can't be found
+                    final List<Object> arguments = FacebookMethodsTypeHelper.getArguments(method.getName());
+                    final int nArgs = arguments.size() / 2;
+                    List<Class> types = new ArrayList<Class>(nArgs);
+                    for (int i = 0; i < nArgs; i++) {
+                        types.add((Class) arguments.get(2 * i));
+                    }
+                    assertTrue("Missing parameters for " + method,
+                        types.containsAll(Arrays.asList(method.getParameterTypes())));
+                }
+            }
+        }
+    }
+
+    @Test
+    public void testAllArguments() throws Exception {
+        assertFalse("Missing arguments", FacebookMethodsTypeHelper.allArguments().isEmpty());
+    }
+
+    @Test
+    public void testGetType() throws Exception {
+        for (Field field : FacebookEndpointConfiguration.class.getDeclaredFields()) {
+            Class expectedType = field.getType();
+            final Class actualType = FacebookMethodsTypeHelper.getType(field.getName());
+            // test for auto boxing, un-boxing
+            if (actualType.isPrimitive()) {
+                expectedType = (Class) expectedType.getField("TYPE").get(null);
+            } else if (List.class.isAssignableFrom(expectedType) && actualType.isArray()) {
+                // skip lists, since they will be converted in invokeMethod()
+                expectedType = actualType;
+            }
+            assertEquals("Missing property " + field.getName(), expectedType, actualType);
+        }
+    }
+
+    @Test
+    public void testConvertToGetMethod() throws Exception {
+        assertEquals("Invalid get method name",
+            FacebookMethodsType.GET_ACCOUNTS.getName(), FacebookMethodsTypeHelper.convertToGetMethod("accounts"));
+    }
+
+    @Test
+    public void testConvertToSearchMethod() throws Exception {
+        assertEquals("Invalid search method name",
+            FacebookMethodsType.SEARCHPOSTS.getName(), FacebookMethodsTypeHelper.convertToSearchMethod("posts"));
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java
new file mode 100644
index 0000000..1f390e4
--- /dev/null
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java
@@ -0,0 +1,47 @@
+/**
+ * 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.facebook.data;
+
+import java.lang.reflect.Method;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+
+import facebook4j.Facebook;
+import org.junit.Test;
+
+/**
+ * Test that all *Methods methods are mapped in {@link FacebookMethodsType}.
+ */
+public class FacebookMethodsTypeTest {
+
+    @Test
+    public void areAllMethodsMapped() throws Exception {
+        final Class<?>[] interfaces = Facebook.class.getInterfaces();
+        for (Class clazz : interfaces) {
+            if (clazz.getName().endsWith("Methods")) {
+                // check all methods of this *Methods interface
+                for (Method method : clazz.getDeclaredMethods()) {
+                    final FacebookMethodsType methodsType = FacebookMethodsType.findMethod(method.getName(), method.getParameterTypes());
+                    assertNotNull(methodsType);
+                    assertEquals("Methods are not equal", method, methodsType.getMethod());
+                }
+            }
+        }
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java
new file mode 100644
index 0000000..e58d0d7
--- /dev/null
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java
@@ -0,0 +1,63 @@
+package org.apache.camel.component.facebook.data;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.Locale;
+import java.util.Map;
+
+import static org.junit.Assert.*;
+
+import facebook4j.Reading;
+import org.apache.camel.component.facebook.FacebookConstants;
+import org.junit.Test;
+
+/**
+ * Test {@link ReadingBuilder}. 
+ */
+public class ReadingBuilderTest {
+
+    @Test
+    public void testCopy() throws Exception {
+        final Reading source = new Reading();
+        source.fields("field1", "field2");
+        source.filter("testFilter");
+        source.limit(100);
+        source.locale(Locale.US);
+        source.metadata();
+        source.offset(1000);
+        source.since(new Date());
+        source.until(new Date());
+        source.withLocation();
+        
+        Reading copy = ReadingBuilder.copy(source, false);
+        assertNotNull("Null copy", copy);
+        assertEquals("Copy not equal", source.toString(), copy.toString());
+
+        // skip since and until
+        copy = ReadingBuilder.copy(source, true);
+        assertNotEquals("Copy equal", source.toString(), copy.toString());
+        assertFalse("since", copy.toString().contains("since="));
+        assertFalse("until", copy.toString().contains("until="));
+    }
+
+    @Test
+    public void testSetProperties() throws Exception {
+        final Reading reading = new Reading();
+
+        Map<String, Object> properties = new HashMap<String, Object>();
+        properties.put("fields", "field1,field2");
+        properties.put("filter", "testFilter");
+        properties.put("limit", "100");
+        properties.put("metadata", "");
+        properties.put("offset", "1000");
+        final String facebookDate = new SimpleDateFormat(FacebookConstants.FACEBOOK_DATE_FORMAT).format(new Date());
+        properties.put("since", facebookDate);
+        properties.put("until", facebookDate);
+        properties.put("withLocation", "");
+
+        // set properties on Reading
+        ReadingBuilder.setProperties(reading, properties);
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/resources/log4j.properties
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/resources/log4j.properties b/components/camel-facebook/src/test/resources/log4j.properties
new file mode 100644
index 0000000..f4153d6
--- /dev/null
+++ b/components/camel-facebook/src/test/resources/log4j.properties
@@ -0,0 +1,31 @@
+## ---------------------------------------------------------------------------
+## 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.
+## ---------------------------------------------------------------------------
+
+#
+# The logging properties used during tests..
+#
+log4j.rootLogger=INFO, out
+
+# uncomment the following line to turn on Camel debugging
+#log4j.logger.org.apache.camel=DEBUG
+
+# CONSOLE appender not used by default
+log4j.appender.out=org.apache.log4j.ConsoleAppender
+log4j.appender.out.layout=org.apache.log4j.PatternLayout
+log4j.appender.out.layout.ConversionPattern=[%30.30t] %-30.30c{1} %-5p %m%n
+#log4j.appender.out.layout.ConversionPattern=%d [%-15.15t] %-5p %-30.30c{1} - %m%n
+

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/resources/test-options.properties
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/resources/test-options.properties b/components/camel-facebook/src/test/resources/test-options.properties
new file mode 100644
index 0000000..ab2a99f
--- /dev/null
+++ b/components/camel-facebook/src/test/resources/test-options.properties
@@ -0,0 +1,20 @@
+## ---------------------------------------------------------------------------
+## 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.
+## ---------------------------------------------------------------------------
+
+oAuthAppId=<app-id>
+oAuthAppSecret=<app-secret>
+oAuthAccessToken=<access-token>

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/pom.xml
----------------------------------------------------------------------
diff --git a/components/pom.xml b/components/pom.xml
index 89b981b..811c702 100644
--- a/components/pom.xml
+++ b/components/pom.xml
@@ -81,6 +81,7 @@
     <module>camel-elasticsearch</module>
     <module>camel-eventadmin</module>
     <module>camel-exec</module>
+    <module>camel-facebook</module>
     <module>camel-flatpack</module>
     <module>camel-fop</module>
     <module>camel-freemarker</module>
@@ -239,4 +240,4 @@
       </dependencies>
     </profile>
   </profiles>
-</project>
+</project>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/parent/pom.xml
----------------------------------------------------------------------
diff --git a/parent/pom.xml b/parent/pom.xml
index 83e9684..9d1ab48 100644
--- a/parent/pom.xml
+++ b/parent/pom.xml
@@ -124,6 +124,7 @@
     <el-api-1.0-version>1.0.1</el-api-1.0-version>
     <exec-maven-plugin-version>1.2.1</exec-maven-plugin-version>
     <ezmorph-bundle-version>1.0.6_1</ezmorph-bundle-version>
+    <facebook4j-core-version>1.1.12</facebook4j-core-version>
     <fastinfoset-version>1.2.13_1</fastinfoset-version>
     <felix-configadmin-version>1.4.0</felix-configadmin-version>
     <felix-fileinstall-version>3.2.6</felix-fileinstall-version>

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/platforms/karaf/features/src/main/resources/features.xml
----------------------------------------------------------------------
diff --git a/platforms/karaf/features/src/main/resources/features.xml b/platforms/karaf/features/src/main/resources/features.xml
index 4e18ca0..8e67404 100644
--- a/platforms/karaf/features/src/main/resources/features.xml
+++ b/platforms/karaf/features/src/main/resources/features.xml
@@ -269,6 +269,11 @@
     <bundle dependency='true'>mvn:commons-io/commons-io/${commons-io-version}</bundle>
     <bundle>mvn:org.apache.camel/camel-exec/${project.version}</bundle>
   </feature>
+  <feature name='camel-facebook' version='${project.version}' resolver='(obr)' start-level='50'>
+    <feature version='${project.version}'>camel-core</feature>
+    <bundle dependency='true'>wrap:mvn:org.facebook4j/facebook4j-core/${facebook4j-core-version}</bundle>
+    <bundle>mvn:org.apache.camel/camel-facebook/${project.version}</bundle>
+  </feature>
   <feature name='camel-flatpack' version='${project.version}' resolver='(obr)' start-level='50'>
     <feature version='${project.version}'>camel-core</feature>
     <bundle dependency='true'>mvn:org.apache.servicemix.bundles/org.apache.servicemix.bundles.jdom/${jdom-bundle-version}</bundle>


[4/4] git commit: CAMEL-6676 Fixed some CS errors and eclipse warnings of camel-facebook

Posted by ni...@apache.org.
CAMEL-6676 Fixed some CS errors and eclipse warnings of camel-facebook


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/124c0e34
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/124c0e34
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/124c0e34

Branch: refs/heads/master
Commit: 124c0e3445d33399dec1976ae4783e464f6af380
Parents: 1c29340
Author: Willem Jiang <ni...@apache.org>
Authored: Sun Sep 1 15:47:15 2013 +0800
Committer: Willem Jiang <ni...@apache.org>
Committed: Sun Sep 1 15:47:15 2013 +0800

----------------------------------------------------------------------
 components/camel-facebook/pom.xml               |  5 ++-
 .../component/facebook/FacebookConsumer.java    | 16 ++++++--
 .../facebook/config/FacebookConfiguration.java  |  9 ++---
 .../config/FacebookEndpointConfiguration.java   | 14 ++++++-
 .../facebook/data/FacebookMethodsType.java      | 41 ++++++++++++++++++--
 .../data/FacebookMethodsTypeHelper.java         | 17 ++++++--
 .../facebook/data/FacebookPropertiesHelper.java | 11 ++++--
 .../component/facebook/data/ReadingBuilder.java | 11 ++++--
 .../facebook/CamelFacebookTestSupport.java      |  6 +--
 .../facebook/FacebookComponentConsumerTest.java | 11 ++++--
 .../facebook/FacebookComponentProducerTest.java | 23 +++++------
 .../data/FacebookMethodsTypeHelperTest.java     | 40 ++++++++++++++-----
 .../facebook/data/FacebookMethodsTypeTest.java  |  8 ++--
 .../facebook/data/ReadingBuilderTest.java       | 24 +++++++++++-
 14 files changed, 178 insertions(+), 58 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/pom.xml
----------------------------------------------------------------------
diff --git a/components/camel-facebook/pom.xml b/components/camel-facebook/pom.xml
index 940d539..b3745a3 100644
--- a/components/camel-facebook/pom.xml
+++ b/components/camel-facebook/pom.xml
@@ -21,7 +21,7 @@
   <parent>
     <artifactId>components</artifactId>
     <groupId>org.apache.camel</groupId>
-    <version>2.12.1-SNAPSHOT</version>
+    <version>2.13-SNAPSHOT</version>
   </parent>
 
   <artifactId>camel-facebook</artifactId>
@@ -79,7 +79,8 @@
           <forkedProcessTimeoutInSeconds>300</forkedProcessTimeoutInSeconds>
           <includes>
             <!-- Here we only run test of  -->
-            <include>**/*UriConfigurationTest.java</include>
+            <include>**/ReadingBuilderTest.java</include>
+            <include>**/FacebookMethodsType*Test.java</include>
           </includes>
         </configuration>
       </plugin>

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java
index 4980d3c..854214c 100644
--- a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java
@@ -18,11 +18,22 @@ package org.apache.camel.component.facebook;
 
 import java.lang.reflect.Array;
 import java.text.SimpleDateFormat;
-import java.util.*;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
 import java.util.concurrent.TimeUnit;
+
+import facebook4j.Reading;
+
 import org.apache.camel.Exchange;
 import org.apache.camel.Processor;
 import org.apache.camel.component.facebook.data.FacebookMethodsType;
+import org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.MatchType;
 import org.apache.camel.component.facebook.data.FacebookPropertiesHelper;
 import org.apache.camel.component.facebook.data.ReadingBuilder;
 import org.apache.camel.impl.ScheduledPollConsumer;
@@ -30,12 +41,9 @@ import org.apache.camel.util.ObjectHelper;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import facebook4j.Reading;
-
 import static org.apache.camel.component.facebook.FacebookConstants.FACEBOOK_DATE_FORMAT;
 import static org.apache.camel.component.facebook.FacebookConstants.READING_PPROPERTY;
 import static org.apache.camel.component.facebook.FacebookConstants.READING_PREFIX;
-import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.MatchType;
 import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.filterMethods;
 import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getHighestPriorityMethod;
 import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getMissingProperties;

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java
index 5285423..20a2ebb 100644
--- a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java
@@ -16,17 +16,16 @@
  */
 package org.apache.camel.component.facebook.config;
 
-import org.apache.camel.spi.UriParam;
-import org.apache.camel.spi.UriParams;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
 import facebook4j.Facebook;
 import facebook4j.FacebookException;
 import facebook4j.FacebookFactory;
 import facebook4j.auth.OAuthAuthorization;
 import facebook4j.conf.Configuration;
 import facebook4j.conf.ConfigurationBuilder;
+import org.apache.camel.spi.UriParam;
+import org.apache.camel.spi.UriParams;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 
 /**
  * Facebook component configuration.

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java
index 1705630..66c8127 100644
--- a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java
@@ -22,13 +22,23 @@ import java.util.Arrays;
 import java.util.List;
 import java.util.Locale;
 import java.util.Map;
+
+import facebook4j.AlbumCreate;
+import facebook4j.CheckinCreate;
+import facebook4j.EventUpdate;
+import facebook4j.GeoLocation;
+import facebook4j.Media;
+import facebook4j.PictureSize;
+import facebook4j.PostUpdate;
+import facebook4j.Reading;
+import facebook4j.TagUpdate;
+import facebook4j.TestUser;
+
 import org.apache.camel.component.facebook.FacebookConstants;
 import org.apache.camel.spi.UriParam;
 import org.apache.camel.spi.UriParams;
 import org.apache.camel.util.ObjectHelper;
 
-import facebook4j.*;
-
 @UriParams
 public class FacebookEndpointConfiguration extends FacebookConfiguration {
 

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java
index 02ef2fd..f35fb1a 100644
--- a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java
@@ -18,12 +18,45 @@ package org.apache.camel.component.facebook.data;
 
 import java.lang.reflect.Method;
 import java.net.URL;
-import java.util.*;
-import org.apache.camel.component.facebook.FacebookConstants;
-
-import facebook4j.*;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+
+import facebook4j.Album;
+import facebook4j.AlbumCreate;
+import facebook4j.Checkin;
+import facebook4j.CheckinCreate;
+import facebook4j.Comment;
+import facebook4j.Domain;
+import facebook4j.Event;
+import facebook4j.EventUpdate;
+import facebook4j.Facebook;
+import facebook4j.Friendlist;
+import facebook4j.GeoLocation;
+import facebook4j.Group;
+import facebook4j.InboxResponseList;
+import facebook4j.Link;
+import facebook4j.Media;
+import facebook4j.Message;
+import facebook4j.Note;
+import facebook4j.Photo;
+import facebook4j.PictureSize;
+import facebook4j.Post;
+import facebook4j.PostUpdate;
+import facebook4j.Question;
+import facebook4j.Reading;
+import facebook4j.ResponseList;
+import facebook4j.TagUpdate;
+import facebook4j.TestUser;
+import facebook4j.User;
+import facebook4j.Video;
 import facebook4j.internal.org.json.JSONArray;
 
+import org.apache.camel.component.facebook.FacebookConstants;
+
 /**
  * Enum for Facebook4J *Method interfaces.
  * The methods are ordered by the number and nature of arguments.

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java
index 1e78dac..0779d71 100644
--- a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java
@@ -17,16 +17,25 @@
 package org.apache.camel.component.facebook.data;
 
 import java.lang.reflect.Array;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import facebook4j.Facebook;
+import facebook4j.FacebookException;
+
 import org.apache.camel.RuntimeCamelException;
 import org.apache.camel.component.facebook.FacebookConstants;
 import org.apache.camel.component.facebook.config.FacebookNameStyle;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import facebook4j.Facebook;
-import facebook4j.FacebookException;
-
 
 /**
  * Helper class for working with {@link FacebookMethodsType}.

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java
index 5a61d2c..b17a120 100644
--- a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java
@@ -17,7 +17,14 @@
 package org.apache.camel.component.facebook.data;
 
 import java.lang.reflect.Field;
-import java.util.*;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+import facebook4j.Reading;
+
 import org.apache.camel.Exchange;
 import org.apache.camel.component.facebook.FacebookConstants;
 import org.apache.camel.component.facebook.config.FacebookConfiguration;
@@ -26,8 +33,6 @@ import org.apache.camel.util.IntrospectionSupport;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import facebook4j.Reading;
-
 /**
  * Helper class to work with Facebook component properties.
  */

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java
index 1e44887..40c4b2f 100644
--- a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java
@@ -22,14 +22,19 @@ import java.text.SimpleDateFormat;
 import java.util.LinkedHashMap;
 import java.util.Locale;
 import java.util.Map;
-import org.apache.camel.component.facebook.FacebookConstants;
 
 import facebook4j.Reading;
 
+import org.apache.camel.component.facebook.FacebookConstants;
+
 /**
  * Builds {@link facebook4j.Reading} instances.
  */
-public class ReadingBuilder {
+public final class ReadingBuilder {
+    
+    private ReadingBuilder() {
+        // Helper class
+    }
 
 
     public static Reading copy(Reading reading, boolean skipSinceUtil) throws NoSuchFieldException, IllegalAccessException {
@@ -39,7 +44,7 @@ public class ReadingBuilder {
         final LinkedHashMap<String, String> source = (LinkedHashMap<String, String>) field.get(reading);
         // create another reading, and add all fields from source
         Reading copy = new Reading();
-        final LinkedHashMap copyMap = new LinkedHashMap();
+        final LinkedHashMap<String, String> copyMap = new LinkedHashMap<String, String>();
         copyMap.putAll(source);
         if (skipSinceUtil) {
             copyMap.remove("since");

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java
index 1dc0f17..98d28fb 100644
--- a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java
@@ -64,9 +64,9 @@ public class CamelFacebookTestSupport extends CamelTestSupport {
     }
 
     public String getOauthParams() {
-        return "oAuthAppId=" + properties.get("oAuthAppId") + "&oAuthAppSecret=" + properties.get("oAuthAppSecret") +
-            (properties.get("oAuthAccessToken") != null ?
-                ("&oAuthAccessToken=" + properties.get("oAuthAccessToken")) : "");
+        return "oAuthAppId=" + properties.get("oAuthAppId") + "&oAuthAppSecret=" + properties.get("oAuthAppSecret")
+            + (properties.get("oAuthAccessToken") != null
+            ? ("&oAuthAccessToken=" + properties.get("oAuthAccessToken")) : "");
     }
 
     protected String getShortName(String name) {

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java
index 80476fc..b64832b 100644
--- a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java
@@ -18,14 +18,19 @@ package org.apache.camel.component.facebook;
 
 import java.lang.reflect.Method;
 import java.text.SimpleDateFormat;
-import java.util.*;
+import java.util.Arrays;
+import java.util.Date;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
 import java.util.concurrent.TimeUnit;
+
+import facebook4j.api.SearchMethods;
+
 import org.apache.camel.builder.RouteBuilder;
 import org.apache.camel.component.mock.MockEndpoint;
 import org.junit.Test;
 
-import facebook4j.api.SearchMethods;
-
 public class FacebookComponentConsumerTest extends CamelFacebookTestSupport {
 
     private final Set<String> searchNames = new HashSet<String>();

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java
index bc8b65b..21e4709 100644
--- a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java
@@ -21,12 +21,13 @@ import java.util.Arrays;
 import java.util.HashSet;
 import java.util.List;
 import java.util.Set;
+
+import facebook4j.Facebook;
+
 import org.apache.camel.builder.RouteBuilder;
 import org.apache.camel.component.mock.MockEndpoint;
 import org.junit.Test;
 
-import facebook4j.Facebook;
-
 public class FacebookComponentProducerTest extends CamelFacebookTestSupport {
 
     private final Set<String> noArgNames = new HashSet<String>();
@@ -35,7 +36,7 @@ public class FacebookComponentProducerTest extends CamelFacebookTestSupport {
     private final List<String> readingExcludes;
 
     public FacebookComponentProducerTest() throws Exception {
-        for (Class clazz : Facebook.class.getInterfaces()) {
+        for (Class<?> clazz : Facebook.class.getInterfaces()) {
             final String clazzName = clazz.getSimpleName();
             if (clazzName.endsWith("Methods") && !clazzName.equals("GameMethods")) {
                 for (Method method : clazz.getDeclaredMethods()) {
@@ -94,28 +95,28 @@ public class FacebookComponentProducerTest extends CamelFacebookTestSupport {
                 // generate test routes for all methods with no args
                 for (String name : noArgNames) {
                     from("direct://test" + name)
-                      .to("facebook://" + name + "?" + getOauthParams())
-                      .to("mock:result" + name);
+                        .to("facebook://" + name + "?" + getOauthParams())
+                        .to("mock:result" + name);
 
                     // with user id
                     if (!idExcludes.contains(name)) {
                         from("direct://testId" + name)
-                          .to("facebook://" + name + "?userId=me&" + getOauthParams())
-                          .to("mock:resultId" + name);
+                            .to("facebook://" + name + "?userId=me&" + getOauthParams())
+                            .to("mock:resultId" + name);
                     }
 
                     // reading options
                     if (!readingExcludes.contains(name)) {
                         from("direct://testReading" + name)
-                          .to("facebook://" + name + "?reading.limit=10&reading.locale=en,US&" + getOauthParams())
-                          .to("mock:resultReading" + name);
+                            .to("facebook://" + name + "?reading.limit=10&reading.locale=en,US&" + getOauthParams())
+                            .to("mock:resultReading" + name);
                     }
 
                     // with id and reading options
                     if (!(idExcludes.contains(name) || readingExcludes.contains(name))) {
                         from("direct://testIdReading" + name)
-                          .to("facebook://" + name + "?userId=me&reading.limit=10&reading.locale=en,US&" + getOauthParams())
-                          .to("mock:resultIdReading" + name);
+                            .to("facebook://" + name + "?userId=me&reading.limit=10&reading.locale=en,US&" + getOauthParams())
+                            .to("mock:resultIdReading" + name);
                     }
                 }
 

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java
index 0cdc15f..a4a43fd 100644
--- a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelperTest.java
@@ -1,17 +1,39 @@
+/**
+ * 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.facebook.data;
 
 import java.lang.reflect.Field;
 import java.lang.reflect.Method;
-import java.util.*;
-import org.apache.camel.component.facebook.config.FacebookEndpointConfiguration;
-import org.junit.Test;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
 
 import facebook4j.Facebook;
 
+import org.apache.camel.component.facebook.config.FacebookEndpointConfiguration;
+import org.junit.Test;
+
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
 
+
 /**
  * Test {@link FacebookMethodsTypeHelper}.
  */
@@ -78,16 +100,16 @@ public class FacebookMethodsTypeHelperTest {
     @Test
     public void testGetArguments() throws Exception {
         final Class<?>[] interfaces = Facebook.class.getInterfaces();
-        for (Class clazz : interfaces) {
+        for (Class<?> clazz : interfaces) {
             if (clazz.getName().endsWith("Methods")) {
                 // check all methods of this *Methods interface
                 for (Method method : clazz.getDeclaredMethods()) {
                     // will throw an exception if can't be found
                     final List<Object> arguments = FacebookMethodsTypeHelper.getArguments(method.getName());
                     final int nArgs = arguments.size() / 2;
-                    List<Class> types = new ArrayList<Class>(nArgs);
+                    List<Class<?>> types = new ArrayList<Class<?>>(nArgs);
                     for (int i = 0; i < nArgs; i++) {
-                        types.add((Class) arguments.get(2 * i));
+                        types.add((Class<?>) arguments.get(2 * i));
                     }
                     assertTrue("Missing parameters for " + method,
                         types.containsAll(Arrays.asList(method.getParameterTypes())));
@@ -104,11 +126,11 @@ public class FacebookMethodsTypeHelperTest {
     @Test
     public void testGetType() throws Exception {
         for (Field field : FacebookEndpointConfiguration.class.getDeclaredFields()) {
-            Class expectedType = field.getType();
-            final Class actualType = FacebookMethodsTypeHelper.getType(field.getName());
+            Class<?> expectedType = field.getType();
+            final Class<?> actualType = FacebookMethodsTypeHelper.getType(field.getName());
             // test for auto boxing, un-boxing
             if (actualType.isPrimitive()) {
-                expectedType = (Class) expectedType.getField("TYPE").get(null);
+                expectedType = (Class<?>) expectedType.getField("TYPE").get(null);
             } else if (List.class.isAssignableFrom(expectedType) && actualType.isArray()) {
                 // skip lists, since they will be converted in invokeMethod()
                 expectedType = actualType;

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java
index 1f390e4..8c3c523 100644
--- a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeTest.java
@@ -18,11 +18,13 @@ package org.apache.camel.component.facebook.data;
 
 import java.lang.reflect.Method;
 
+import facebook4j.Facebook;
+
+import org.junit.Test;
+
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertNotNull;
 
-import facebook4j.Facebook;
-import org.junit.Test;
 
 /**
  * Test that all *Methods methods are mapped in {@link FacebookMethodsType}.
@@ -32,7 +34,7 @@ public class FacebookMethodsTypeTest {
     @Test
     public void areAllMethodsMapped() throws Exception {
         final Class<?>[] interfaces = Facebook.class.getInterfaces();
-        for (Class clazz : interfaces) {
+        for (Class<?> clazz : interfaces) {
             if (clazz.getName().endsWith("Methods")) {
                 // check all methods of this *Methods interface
                 for (Method method : clazz.getDeclaredMethods()) {

http://git-wip-us.apache.org/repos/asf/camel/blob/124c0e34/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java
index e58d0d7..1856228 100644
--- a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/data/ReadingBuilderTest.java
@@ -1,3 +1,19 @@
+/**
+ * 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.facebook.data;
 
 import java.text.SimpleDateFormat;
@@ -6,12 +22,16 @@ import java.util.HashMap;
 import java.util.Locale;
 import java.util.Map;
 
-import static org.junit.Assert.*;
-
 import facebook4j.Reading;
+
 import org.apache.camel.component.facebook.FacebookConstants;
 import org.junit.Test;
 
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNotEquals;
+import static org.junit.Assert.assertNotNull;
+
 /**
  * Test {@link ReadingBuilder}. 
  */


[3/4] git commit: CAMEL-6676 Added camel-facebook component with thanks for Dhiraj

Posted by ni...@apache.org.
CAMEL-6676 Added camel-facebook component with thanks for Dhiraj


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/1c293408
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/1c293408
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/1c293408

Branch: refs/heads/master
Commit: 1c293408328ac6d62219d3da5ea15e0efbc77425
Parents: 81377b0
Author: Willem Jiang <ni...@apache.org>
Authored: Sun Sep 1 15:08:35 2013 +0800
Committer: Willem Jiang <ni...@apache.org>
Committed: Sun Sep 1 15:08:35 2013 +0800

----------------------------------------------------------------------
 components/camel-facebook/pom.xml               | 111 +++
 .../component/facebook/FacebookComponent.java   |  78 ++
 .../component/facebook/FacebookConstants.java   |  39 +
 .../component/facebook/FacebookConsumer.java    | 217 ++++++
 .../component/facebook/FacebookEndpoint.java    | 165 +++++
 .../component/facebook/FacebookProducer.java    | 184 +++++
 .../facebook/config/FacebookConfiguration.java  | 443 ++++++++++++
 .../config/FacebookEndpointConfiguration.java   | 706 +++++++++++++++++++
 .../facebook/config/FacebookNameStyle.java      |  26 +
 .../facebook/data/FacebookMethodsType.java      | 572 +++++++++++++++
 .../data/FacebookMethodsTypeHelper.java         | 366 ++++++++++
 .../facebook/data/FacebookPropertiesHelper.java | 132 ++++
 .../component/facebook/data/ReadingBuilder.java | 121 ++++
 .../org/apache/camel/component/facebook         |   1 +
 .../facebook/CamelFacebookTestSupport.java      |  81 +++
 .../facebook/FacebookComponentConsumerTest.java |  90 +++
 .../facebook/FacebookComponentProducerTest.java | 127 ++++
 .../data/FacebookMethodsTypeHelperTest.java     | 132 ++++
 .../facebook/data/FacebookMethodsTypeTest.java  |  47 ++
 .../facebook/data/ReadingBuilderTest.java       |  63 ++
 .../src/test/resources/log4j.properties         |  31 +
 .../src/test/resources/test-options.properties  |  20 +
 components/pom.xml                              |   3 +-
 parent/pom.xml                                  |   1 +
 .../features/src/main/resources/features.xml    |   5 +
 25 files changed, 3760 insertions(+), 1 deletion(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/pom.xml
----------------------------------------------------------------------
diff --git a/components/camel-facebook/pom.xml b/components/camel-facebook/pom.xml
new file mode 100644
index 0000000..940d539
--- /dev/null
+++ b/components/camel-facebook/pom.xml
@@ -0,0 +1,111 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+  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.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+
+  <modelVersion>4.0.0</modelVersion>
+  <parent>
+    <artifactId>components</artifactId>
+    <groupId>org.apache.camel</groupId>
+    <version>2.12.1-SNAPSHOT</version>
+  </parent>
+
+  <artifactId>camel-facebook</artifactId>
+  <packaging>bundle</packaging>
+  <name>Camel :: Facebook</name>
+  <description>Camel Facebook Support</description>
+
+  <properties>
+    <camel.osgi.export.pkg>org.apache.camel.component.facebook.*</camel.osgi.export.pkg>
+    <camel.osgi.export.service>org.apache.camel.spi.ComponentResolver;component=facebook</camel.osgi.export.service>
+  </properties>
+
+  <dependencies>
+    <dependency>
+      <groupId>org.apache.camel</groupId>
+      <artifactId>camel-core</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.camel</groupId>
+      <artifactId>spi-annotations</artifactId>
+      <version>${project.version}</version>
+    </dependency>
+    <dependency>
+      <groupId>org.facebook4j</groupId>
+      <artifactId>facebook4j-core</artifactId>
+      <version>${facebook4j-core-version}</version>
+    </dependency>
+
+    <!-- testing -->
+    <dependency>
+      <groupId>org.apache.camel</groupId>
+      <artifactId>camel-test</artifactId>
+      <scope>test</scope>
+    </dependency>
+    <dependency>
+      <groupId>junit</groupId>
+      <artifactId>junit</artifactId>
+      <scope>test</scope>
+    </dependency>
+    <dependency>
+      <groupId>org.slf4j</groupId>
+      <artifactId>slf4j-log4j12</artifactId>
+      <scope>test</scope>
+    </dependency>
+  </dependencies>
+
+  <build>
+    <plugins>
+      <plugin>
+        <artifactId>maven-surefire-plugin</artifactId>
+        <configuration>
+          <childDelegation>false</childDelegation>
+          <useFile>true</useFile>
+          <forkMode>once</forkMode>
+          <forkedProcessTimeoutInSeconds>300</forkedProcessTimeoutInSeconds>
+          <includes>
+            <!-- Here we only run test of  -->
+            <include>**/*UriConfigurationTest.java</include>
+          </includes>
+        </configuration>
+      </plugin>
+    </plugins>
+  </build>
+
+  <profiles>
+    <profile>
+      <id>facebook-test</id>
+      <build>
+        <plugins>
+          <plugin>
+            <artifactId>maven-surefire-plugin</artifactId>
+            <configuration>
+              <childDelegation>false</childDelegation>
+              <useFile>true</useFile>
+              <forkMode>once</forkMode>
+              <forkedProcessTimeoutInSeconds>300</forkedProcessTimeoutInSeconds>
+              <includes>
+                <include>**/*Test.java</include>
+              </includes>
+            </configuration>
+          </plugin>
+        </plugins>
+      </build>
+    </profile>
+  </profiles>
+
+</project>

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookComponent.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookComponent.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookComponent.java
new file mode 100644
index 0000000..4ae234f
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookComponent.java
@@ -0,0 +1,78 @@
+/**
+ * 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.facebook;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.Endpoint;
+import org.apache.camel.component.facebook.config.FacebookConfiguration;
+import org.apache.camel.component.facebook.config.FacebookEndpointConfiguration;
+import org.apache.camel.impl.UriEndpointComponent;
+import org.apache.camel.spi.UriParam;
+import org.apache.camel.util.IntrospectionSupport;
+
+/**
+ * Represents the component that manages {@link FacebookEndpoint}.
+ */
+public class FacebookComponent extends UriEndpointComponent {
+
+    @UriParam
+    private FacebookConfiguration configuration;
+
+    public FacebookComponent() {
+        this(new FacebookConfiguration());
+    }
+
+    public FacebookComponent(FacebookConfiguration configuration) {
+        this(null, configuration);
+    }
+
+    public FacebookComponent(CamelContext context) {
+        this(context, new FacebookConfiguration());
+    }
+
+    public FacebookComponent(CamelContext context, FacebookConfiguration configuration) {
+        super(context, FacebookEndpoint.class);
+        this.configuration = configuration;
+    }
+
+    protected Endpoint createEndpoint(String uri, String remaining, Map<String, Object> parameters) throws Exception {
+        FacebookEndpointConfiguration config = copyComponentProperties();
+        return new FacebookEndpoint(uri, this, remaining, config);
+    }
+
+    private FacebookEndpointConfiguration copyComponentProperties() throws Exception {
+        Map<String, Object> componentProperties = new HashMap<String, Object>();
+        IntrospectionSupport.getProperties(configuration, componentProperties, null, false);
+
+        // create endpoint configuration with component properties
+        FacebookEndpointConfiguration config = new FacebookEndpointConfiguration();
+        IntrospectionSupport.setProperties(config, componentProperties, null);
+        return config;
+    }
+
+    public FacebookConfiguration getConfiguration() {
+        return configuration;
+    }
+
+    public void setConfiguration(FacebookConfiguration configuration) {
+        this.configuration = configuration;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConstants.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConstants.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConstants.java
new file mode 100644
index 0000000..eec85dc
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConstants.java
@@ -0,0 +1,39 @@
+/**
+ * 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.facebook;
+
+/**
+ * Common constants.
+ */
+public interface FacebookConstants {
+
+    // reading options property name and prefix for uri property
+    String READING_PPROPERTY = "reading";
+    String READING_PREFIX = READING_PPROPERTY + ".";
+
+    // property name prefix for exchange 'in' headers
+    String FACEBOOK_PROPERTY_PREFIX = "CamelFacebook.";
+
+    // property name for exchange 'in' body
+    String IN_BODY_PROPERTY = "inBody";
+
+    String FACEBOOK_THREAD_PROFILE_NAME = "CamelFacebook";
+
+    // date format used by Facebook Reading since and until fields
+    String FACEBOOK_DATE_FORMAT = "yyyy-MM-dd'T'HH:mm:ssZ";
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java
new file mode 100644
index 0000000..4980d3c
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookConsumer.java
@@ -0,0 +1,217 @@
+/**
+ * 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.facebook;
+
+import java.lang.reflect.Array;
+import java.text.SimpleDateFormat;
+import java.util.*;
+import java.util.concurrent.TimeUnit;
+import org.apache.camel.Exchange;
+import org.apache.camel.Processor;
+import org.apache.camel.component.facebook.data.FacebookMethodsType;
+import org.apache.camel.component.facebook.data.FacebookPropertiesHelper;
+import org.apache.camel.component.facebook.data.ReadingBuilder;
+import org.apache.camel.impl.ScheduledPollConsumer;
+import org.apache.camel.util.ObjectHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import facebook4j.Reading;
+
+import static org.apache.camel.component.facebook.FacebookConstants.FACEBOOK_DATE_FORMAT;
+import static org.apache.camel.component.facebook.FacebookConstants.READING_PPROPERTY;
+import static org.apache.camel.component.facebook.FacebookConstants.READING_PREFIX;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.MatchType;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.filterMethods;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getHighestPriorityMethod;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getMissingProperties;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.invokeMethod;
+
+/**
+ * The Facebook consumer.
+ */
+public class FacebookConsumer extends ScheduledPollConsumer {
+
+    private static final Logger LOG = LoggerFactory.getLogger(FacebookConsumer.class);
+    private static final String SINCE_PREFIX = "since=";
+
+    private final FacebookEndpoint endpoint;
+    private final FacebookMethodsType method;
+    private final Map<String, Object> endpointProperties;
+
+    private String sinceTime;
+    private String untilTime;
+
+    public FacebookConsumer(FacebookEndpoint endpoint, Processor processor) {
+        super(endpoint, processor);
+        this.endpoint = endpoint;
+
+        // determine the consumer method to invoke
+        this.method = findMethod(endpoint.getCandidates());
+
+        // get endpoint properties in a map
+        final HashMap<String, Object> properties = new HashMap<String, Object>();
+        FacebookPropertiesHelper.getEndpointProperties(endpoint.getConfiguration(), properties);
+
+        // skip since and until fields?
+        final Reading reading = (Reading) properties.get(READING_PPROPERTY);
+        if (reading != null) {
+            final String queryString = reading.toString();
+            if (queryString.contains("since=")) {
+                // use the user supplied value to start with
+                final int startIndex = queryString.indexOf(SINCE_PREFIX) + SINCE_PREFIX.length();
+                int endIndex = queryString.indexOf('&', startIndex);
+                if (endIndex == -1) {
+                    endIndex = queryString.length();
+                }
+                this.sinceTime = queryString.substring(startIndex, endIndex).replaceAll("%3(a|A)", ":");
+                LOG.debug("Using supplied property {}since value {}", READING_PREFIX, this.sinceTime);
+            }
+            if (queryString.contains("until=")) {
+                LOG.debug("Overriding configured property {}until", READING_PREFIX);
+            }
+        }
+        this.endpointProperties = Collections.unmodifiableMap(properties);
+    }
+
+    private FacebookMethodsType findMethod(List<FacebookMethodsType> candidates) {
+
+        FacebookMethodsType result;
+        // find one that takes the largest subset of endpoint parameters
+        final Set<String> argNames = new HashSet<String>();
+        argNames.addAll(FacebookPropertiesHelper.getEndpointPropertyNames(endpoint.getConfiguration()));
+
+        // add reading property for polling, if it doesn't already exist!
+        argNames.add(READING_PPROPERTY);
+
+        final String[] argNamesArray = argNames.toArray(new String[argNames.size()]);
+        List<FacebookMethodsType> filteredMethods = filterMethods(
+            endpoint.getCandidates(), MatchType.SUPER_SET, argNamesArray);
+
+        if (filteredMethods.isEmpty()) {
+            throw new IllegalArgumentException(
+                String.format("Missing properties for %s, need one or more from %s",
+                    endpoint.getMethodName(),
+                    getMissingProperties(endpoint.getMethodName(), endpoint.getNameStyle(), argNames)));
+        } else if (filteredMethods.size() == 1) {
+            // single match
+            result = filteredMethods.get(0);
+        } else {
+            result = getHighestPriorityMethod(filteredMethods);
+            LOG.warn("Using highest priority method {} from methods {}", method, filteredMethods);
+        }
+        return result;
+    }
+
+    @Override
+    protected int poll() throws Exception {
+        // Note mark this consumer as not greedy to avoid making too many Facebook calls
+        setGreedy(false);
+
+        // invoke the consumer method
+        final Map<String, Object> args = getMethodArguments();
+        try {
+            Object result = invokeMethod(endpoint.getConfiguration().getFacebook(),
+                method, args);
+
+            // process result according to type
+            if (result != null && (result instanceof Collection || result.getClass().isArray())) {
+                // create an exchange for every element
+                final Object array = getResultAsArray(result);
+                final int length = Array.getLength(array);
+                for (int i = 0; i < length; i++) {
+                    processResult(Array.get(array, i));
+                }
+                return length;
+            } else {
+                processResult(result);
+                return 1; // number of messages polled
+            }
+        } catch (Throwable t) {
+            throw ObjectHelper.wrapRuntimeCamelException(t);
+        }
+    }
+
+    private void processResult(Object result) throws Exception {
+        Exchange exchange = endpoint.createExchange();
+        exchange.getIn().setBody(result);
+        try {
+            // send message to next processor in the route
+            getProcessor().process(exchange);
+        } finally {
+            // log exception if an exception occurred and was not handled
+            if (exchange.getException() != null) {
+                getExceptionHandler().handleException("Error processing exchange", exchange, exchange.getException());
+            }
+        }
+    }
+
+    private Object getResultAsArray(Object result) {
+        if (result.getClass().isArray()) {
+            // no conversion needed
+            return result;
+        }
+        // must be a Collection
+        // TODO add support for Paging using ResponseList
+        Collection collection = (Collection) result;
+        return collection.toArray(new Object[collection.size()]);
+    }
+
+    private Map<String, Object> getMethodArguments() {
+        // start by setting the Reading since and until fields,
+        // these are used to avoid reading duplicate results across polls
+        Map<String, Object> arguments = new HashMap<String, Object>();
+        arguments.putAll(endpointProperties);
+
+        Reading reading = (Reading) arguments.remove(READING_PPROPERTY);
+        if (reading == null) {
+            reading = new Reading();
+        } else {
+            try {
+                reading = ReadingBuilder.copy(reading, true);
+            } catch (NoSuchFieldException e) {
+                throw new IllegalArgumentException(String.format("Error creating property [%s]: %s",
+                    READING_PPROPERTY, e.getMessage()), e);
+            } catch (IllegalAccessException e) {
+                throw new IllegalArgumentException(String.format("Error creating property [%s]: %s",
+                    READING_PPROPERTY, e.getMessage()), e);
+            }
+        }
+
+        // now set since and until for this poll
+        final SimpleDateFormat dateFormat = new SimpleDateFormat(FACEBOOK_DATE_FORMAT);
+        final long currentMillis = System.currentTimeMillis();
+        if (this.sinceTime == null) {
+            // first poll, set this to (current time - initial poll delay)
+            final Date startTime = new Date(currentMillis
+                - TimeUnit.MILLISECONDS.convert(getInitialDelay(), getTimeUnit()));
+            this.sinceTime = dateFormat.format(startTime);
+        } else if (this.untilTime != null) {
+            // use the last 'until' time
+            this.sinceTime = this.untilTime;
+        }
+        this.untilTime = dateFormat.format(new Date(currentMillis));
+
+        reading.since(this.sinceTime);
+        reading.until(this.untilTime);
+
+        arguments.put(READING_PPROPERTY, reading);
+
+        return arguments;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookEndpoint.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookEndpoint.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookEndpoint.java
new file mode 100644
index 0000000..0031421
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookEndpoint.java
@@ -0,0 +1,165 @@
+/**
+ * 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.facebook;
+
+import java.util.*;
+import org.apache.camel.Consumer;
+import org.apache.camel.Processor;
+import org.apache.camel.Producer;
+import org.apache.camel.component.facebook.config.FacebookEndpointConfiguration;
+import org.apache.camel.component.facebook.config.FacebookNameStyle;
+import org.apache.camel.component.facebook.data.FacebookMethodsType;
+import org.apache.camel.component.facebook.data.FacebookPropertiesHelper;
+import org.apache.camel.impl.DefaultEndpoint;
+import org.apache.camel.spi.UriEndpoint;
+import org.apache.camel.spi.UriParam;
+import org.apache.camel.util.EndpointHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.convertToGetMethod;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.convertToSearchMethod;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getCandidateMethods;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getMissingProperties;
+import static org.apache.camel.component.facebook.data.FacebookPropertiesHelper.getEndpointPropertyNames;
+
+/**
+ * Represents a Facebook endpoint.
+ */
+@UriEndpoint(scheme = "facebook", consumerClass = FacebookConsumer.class)
+public class FacebookEndpoint extends DefaultEndpoint implements FacebookConstants {
+
+    private static final Logger LOG = LoggerFactory.getLogger(FacebookEndpoint.class);
+
+    @UriParam
+    private FacebookEndpointConfiguration configuration;
+
+    // Facebook4J method name
+    private final String methodName;
+    private FacebookNameStyle nameStyle;
+
+    // candidate methods based on method name and endpoint configuration
+    private List<FacebookMethodsType> candidates;
+
+    public FacebookEndpoint(String uri, FacebookComponent facebookComponent,
+                            String remaining, FacebookEndpointConfiguration configuration) {
+        super(uri, facebookComponent);
+        this.configuration = configuration;
+        this.methodName = remaining;
+    }
+
+    public Producer createProducer() throws Exception {
+        return new FacebookProducer(this);
+    }
+
+    public Consumer createConsumer(Processor processor) throws Exception {
+        final FacebookConsumer consumer = new FacebookConsumer(this, processor);
+        // also set consumer.* properties
+        configureConsumer(consumer);
+        return consumer;
+    }
+
+    public boolean isSingleton() {
+        return true;
+    }
+
+    @Override
+    public void configureProperties(Map<String, Object> options) {
+        super.configureProperties(options);
+
+        // set configuration properties first
+        try {
+            if (configuration == null) {
+                configuration = new FacebookEndpointConfiguration();
+            }
+            EndpointHelper.setReferenceProperties(getCamelContext(), configuration, options);
+            EndpointHelper.setProperties(getCamelContext(), configuration, options);
+        } catch (Exception e) {
+            throw new IllegalArgumentException(e.getMessage(), e);
+        }
+
+        // extract reading properties
+        FacebookPropertiesHelper.configureReadingProperties(configuration, options);
+
+        // validate configuration
+        configuration.validate();
+        // validate and initialize state
+        initState();
+    }
+
+    private void initState() {
+        // get endpoint property names
+        final Set<String> arguments = getEndpointPropertyNames(configuration);
+        final String[] argNames = arguments.toArray(new String[arguments.size()]);
+
+        candidates = new ArrayList<FacebookMethodsType>();
+        candidates.addAll(getCandidateMethods(methodName, argNames));
+        if (!candidates.isEmpty()) {
+            // found an exact name match, allows disambiguation if needed
+            this.nameStyle = FacebookNameStyle.EXACT;
+        } else {
+
+            // also search for long forms of method name, both get* and search*
+            // Note that this set will be further sorted by Producers and Consumers
+            // producers will prefer get* forms, and consumers should prefer search* forms
+            candidates.addAll(getCandidateMethods(convertToGetMethod(methodName), argNames));
+            if (!candidates.isEmpty()) {
+                this.nameStyle = FacebookNameStyle.GET;
+            }
+
+            candidates.addAll(getCandidateMethods(convertToSearchMethod(methodName), argNames));
+            // error if there are no candidates
+            if (candidates.isEmpty()) {
+                throw new IllegalArgumentException(
+                    String.format("No matching operation for %s, with arguments %s", methodName, arguments));
+            }
+
+            if (nameStyle == null) {
+                // no get* methods found
+                nameStyle = FacebookNameStyle.SEARCH;
+            } else {
+                // get* and search* methods found
+                nameStyle = FacebookNameStyle.GET_AND_SEARCH;
+            }
+        }
+
+        // log missing/extra properties for debugging
+        if (LOG.isDebugEnabled()) {
+            final Set<String> missing = getMissingProperties(methodName, nameStyle, arguments);
+            if (!missing.isEmpty()) {
+                LOG.debug("Method {} could use one or more properties from {}", methodName, missing);
+            }
+        }
+    }
+
+    public FacebookEndpointConfiguration getConfiguration() {
+        return configuration;
+    }
+
+    public String getMethodName() {
+        return methodName;
+    }
+
+    public FacebookNameStyle getNameStyle() {
+        return nameStyle;
+    }
+
+    public List<FacebookMethodsType> getCandidates() {
+        return Collections.unmodifiableList(candidates);
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookProducer.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookProducer.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookProducer.java
new file mode 100644
index 0000000..cb585f7
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/FacebookProducer.java
@@ -0,0 +1,184 @@
+/**
+ * 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.facebook;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ExecutorService;
+import org.apache.camel.AsyncCallback;
+import org.apache.camel.CamelContext;
+import org.apache.camel.Exchange;
+import org.apache.camel.RuntimeCamelException;
+import org.apache.camel.component.facebook.config.FacebookEndpointConfiguration;
+import org.apache.camel.component.facebook.data.FacebookMethodsType;
+import org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper;
+import org.apache.camel.impl.DefaultAsyncProducer;
+import org.apache.camel.spi.ExecutorServiceManager;
+import org.apache.camel.spi.ThreadPoolProfile;
+import org.apache.camel.util.ObjectHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.MatchType;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.filterMethods;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getCandidateMethods;
+import static org.apache.camel.component.facebook.data.FacebookMethodsTypeHelper.getMissingProperties;
+import static org.apache.camel.component.facebook.data.FacebookPropertiesHelper.getEndpointProperties;
+import static org.apache.camel.component.facebook.data.FacebookPropertiesHelper.getExchangeProperties;
+
+/**
+ * The Facebook producer.
+ */
+public class FacebookProducer extends DefaultAsyncProducer {
+    private static final transient Logger LOG = LoggerFactory.getLogger(FacebookProducer.class);
+
+    // thread pool executor
+    private static ExecutorService executorService;
+
+    private FacebookEndpoint endpoint;
+
+    public FacebookProducer(FacebookEndpoint endpoint) {
+        super(endpoint);
+        this.endpoint = endpoint;
+
+        // get candidate methods using endpoint configuration
+        getCandidateMethods(endpoint.getEndpointUri());
+    }
+
+    @Override
+    public boolean process(final Exchange exchange, final AsyncCallback callback) {
+        // properties for method arguments
+        final Map<String, Object> properties = new HashMap<String, Object>();
+        getEndpointProperties(endpoint.getConfiguration(), properties);
+        getExchangeProperties(exchange, properties);
+
+        // decide which method to invoke
+        final FacebookMethodsType method = findMethod(exchange, properties);
+        if (method == null) {
+            // synchronous failure
+            callback.done(true);
+            return true;
+        }
+
+        // create a runnable invocation task to be submitted on a background thread pool
+        // this way we avoid blocking the current thread for long running operations
+        Runnable invocation = new Runnable() {
+            @Override
+            public void run() {
+                try {
+                    if (LOG.isDebugEnabled()) {
+                        LOG.debug("Invoking method {} with {}", method.getName(), properties.keySet());
+                    }
+
+                    Object result = FacebookMethodsTypeHelper.invokeMethod(
+                        endpoint.getConfiguration().getFacebook(), method, properties);
+
+                    // producer returns a single response, even for methods with List return types
+                    exchange.getOut().setBody(result);
+                    // copy headers
+                    exchange.getOut().setHeaders(exchange.getIn().getHeaders());
+
+                } catch (Throwable t) {
+                    exchange.setException(ObjectHelper.wrapRuntimeCamelException(t));
+                } finally {
+                    callback.done(false);
+                }
+            }
+        };
+
+        getExecutorService(getEndpoint().getCamelContext()).submit(invocation);
+        return false;
+    }
+
+    private FacebookMethodsType findMethod(Exchange exchange, Map<String, Object> properties) {
+
+        FacebookMethodsType method = null;
+        final List<FacebookMethodsType> candidates = endpoint.getCandidates();
+        if (processInBody(exchange, properties)) {
+
+            // filter candidates based on endpoint and exchange properties
+            final Set<String> argNames = properties.keySet();
+            final List<FacebookMethodsType> filteredMethods = filterMethods(candidates, MatchType.SUPER_SET,
+                argNames.toArray(new String[argNames.size()]));
+
+            // get the method to call
+            if (filteredMethods.isEmpty()) {
+                final Set<String> missing = getMissingProperties(endpoint.getMethodName(),
+                    endpoint.getNameStyle(), argNames);
+                throw new RuntimeCamelException(String.format("Missing properties for %s, need one or more from %s",
+                        endpoint.getMethodName(), missing));
+            } else if (filteredMethods.size() == 1) {
+                // found an exact match
+                method = filteredMethods.get(0);
+            } else {
+                method = FacebookMethodsTypeHelper.getHighestPriorityMethod(filteredMethods);
+                LOG.warn("Calling highest priority method {} from methods {}", method, filteredMethods);
+            }
+        }
+
+        return method;
+    }
+
+    // returns false on exception, which is set in exchange
+    private boolean processInBody(Exchange exchange, Map<String, Object> properties) {
+        final String inBodyProperty = (String) properties.remove(FacebookConstants.IN_BODY_PROPERTY);
+        if (inBodyProperty != null) {
+
+            Object value = exchange.getIn().getBody();
+            try {
+                value = getEndpoint().getCamelContext().getTypeConverter().mandatoryConvertTo(
+                    FacebookEndpointConfiguration.class.getDeclaredField(inBodyProperty).getClass(),
+                    exchange, value);
+            } catch (Exception e) {
+                exchange.setException(new RuntimeCamelException(String.format(
+                    "Error converting value %s to property %s: %s", value, inBodyProperty, e.getMessage()), e));
+
+                return false;
+            }
+
+            properties.put(inBodyProperty, value);
+        }
+
+        return true;
+    }
+
+    protected static synchronized ExecutorService getExecutorService(CamelContext context) {
+        // CamelContext will shutdown thread pool when it shutdown so we can
+        // lazy create it on demand
+        // but in case of hot-deploy or the likes we need to be able to
+        // re-create it (its a shared static instance)
+        if (executorService == null || executorService.isTerminated() || executorService.isShutdown()) {
+            final ExecutorServiceManager manager = context.getExecutorServiceManager();
+
+            // try to lookup a pool first based on profile
+            ThreadPoolProfile poolProfile = manager.getThreadPoolProfile(
+                FacebookConstants.FACEBOOK_THREAD_PROFILE_NAME);
+            if (poolProfile == null) {
+                poolProfile = manager.getDefaultThreadPoolProfile();
+            }
+
+            // create a new pool using the custom or default profile
+            executorService = manager.newScheduledThreadPool(FacebookProducer.class,
+                FacebookConstants.FACEBOOK_THREAD_PROFILE_NAME, poolProfile);
+        }
+
+        return executorService;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java
new file mode 100644
index 0000000..5285423
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookConfiguration.java
@@ -0,0 +1,443 @@
+/**
+ * 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.facebook.config;
+
+import org.apache.camel.spi.UriParam;
+import org.apache.camel.spi.UriParams;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import facebook4j.Facebook;
+import facebook4j.FacebookException;
+import facebook4j.FacebookFactory;
+import facebook4j.auth.OAuthAuthorization;
+import facebook4j.conf.Configuration;
+import facebook4j.conf.ConfigurationBuilder;
+
+/**
+ * Facebook component configuration.
+ */
+@UriParams
+public class FacebookConfiguration implements Cloneable {
+
+    private static final Logger LOG = LoggerFactory.getLogger(FacebookConfiguration.class);
+
+    @UriParam
+    private String oAuthAppId;
+    @UriParam
+    private String oAuthAppSecret;
+    @UriParam
+    private String oAuthAccessToken;
+    @UriParam
+    private String oAuthAuthorizationURL;
+    @UriParam
+    private String oAuthPermissions;
+
+    @UriParam
+    private String oAuthAccessTokenURL;
+    @UriParam
+    private String clientURL;
+    @UriParam
+    private String clientVersion;
+    @UriParam
+    private Boolean debugEnabled;
+    @UriParam
+    private Boolean gzipEnabled;
+    @UriParam
+    private Integer httpConnectionTimeout;
+    @UriParam
+    private Integer httpDefaultMaxPerRoute;
+    @UriParam
+    private Integer httpMaxTotalConnections;
+    @UriParam
+    private String httpProxyHost;
+    @UriParam
+    private String httpProxyPassword;
+    @UriParam
+    private Integer httpProxyPort;
+    @UriParam
+    private String httpProxyUser;
+    @UriParam
+    private Integer httpReadTimeout;
+    @UriParam
+    private Integer httpRetryCount;
+    @UriParam
+    private Integer httpRetryIntervalSeconds;
+    @UriParam
+    private Integer httpStreamingReadTimeout;
+    @UriParam
+    private Boolean jsonStoreEnabled;
+    @UriParam
+    private Boolean mbeanEnabled;
+    @UriParam
+    private Boolean prettyDebugEnabled;
+    @UriParam
+    private String restBaseURL;
+    @UriParam
+    private Boolean useSSL;
+    @UriParam
+    private String videoBaseURL;
+
+    // cached FaceBook instance, is created in getFacebook by endpoint producers and consumers
+    private Facebook facebook;
+
+    public Configuration getConfiguration() {
+        final ConfigurationBuilder builder = new ConfigurationBuilder();
+        // apply builder settings
+
+        if (oAuthAccessToken != null) {
+            builder.setOAuthAccessToken(oAuthAccessToken);
+        }
+        if (oAuthAccessTokenURL != null) {
+            builder.setOAuthAccessTokenURL(oAuthAccessTokenURL);
+        }
+        if (oAuthAppId != null) {
+            builder.setOAuthAppId(oAuthAppId);
+        }
+        if (oAuthAppSecret != null) {
+            builder.setOAuthAppSecret(oAuthAppSecret);
+        }
+        if (oAuthAuthorizationURL != null) {
+            builder.setOAuthAuthorizationURL(oAuthAuthorizationURL);
+        }
+        if (oAuthPermissions != null) {
+            builder.setOAuthPermissions(oAuthPermissions);
+        }
+
+        if (clientURL != null) {
+            builder.setClientURL(clientURL);
+        }
+        if (clientVersion != null) {
+            builder.setClientVersion(clientVersion);
+        }
+        if (debugEnabled != null) {
+            builder.setDebugEnabled(debugEnabled);
+        }
+        if (gzipEnabled != null) {
+            builder.setGZIPEnabled(gzipEnabled);
+        }
+        if (httpConnectionTimeout != null) {
+            builder.setHttpConnectionTimeout(httpConnectionTimeout);
+        }
+        if (httpDefaultMaxPerRoute != null) {
+            builder.setHttpDefaultMaxPerRoute(httpDefaultMaxPerRoute);
+        }
+        if (httpMaxTotalConnections != null) {
+            builder.setHttpMaxTotalConnections(httpMaxTotalConnections);
+        }
+        if (httpProxyHost != null) {
+            builder.setHttpProxyHost(httpProxyHost);
+        }
+        if (httpProxyPassword != null) {
+            builder.setHttpProxyPassword(httpProxyPassword);
+        }
+        if (httpProxyPort != null) {
+            builder.setHttpProxyPort(httpProxyPort);
+        }
+        if (httpProxyUser != null) {
+            builder.setHttpProxyUser(httpProxyUser);
+        }
+        if (httpReadTimeout != null) {
+            builder.setHttpReadTimeout(httpReadTimeout);
+        }
+        if (httpRetryCount != null) {
+            builder.setHttpRetryCount(httpRetryCount);
+        }
+        if (httpRetryIntervalSeconds != null) {
+            builder.setHttpRetryIntervalSeconds(httpRetryIntervalSeconds);
+        }
+        if (httpStreamingReadTimeout != null) {
+            builder.setHttpStreamingReadTimeout(httpStreamingReadTimeout);
+        }
+        if (jsonStoreEnabled != null) {
+            builder.setJSONStoreEnabled(jsonStoreEnabled);
+        }
+        if (mbeanEnabled != null) {
+            builder.setMBeanEnabled(mbeanEnabled);
+        }
+        if (prettyDebugEnabled != null) {
+            builder.setPrettyDebugEnabled(prettyDebugEnabled);
+        }
+        if (restBaseURL != null) {
+            builder.setRestBaseURL(restBaseURL);
+        }
+        if (useSSL != null) {
+            builder.setUseSSL(useSSL);
+        }
+        if (videoBaseURL != null) {
+            builder.setVideoBaseURL(videoBaseURL);
+        }
+
+        return builder.build();
+    }
+
+    /**
+     * Returns {@link Facebook} instance. If needed, creates one from configuration.
+     * @return {@link Facebook} instance
+     */
+    public Facebook getFacebook() throws FacebookException {
+        if (facebook == null) {
+            final Configuration configuration = getConfiguration();
+            FacebookFactory factory = new FacebookFactory(configuration);
+            if (this.oAuthAccessToken == null) {
+                // app login
+                facebook = factory.getInstance(new OAuthAuthorization(configuration));
+                // also get the App access token
+                facebook.getOAuthAppAccessToken();
+                LOG.warn("Login with app id and secret, access to some APIs is restricted!");
+            } else {
+                // user login with token
+                facebook = factory.getInstance();
+                // verify the access token
+                facebook.getOAuthAccessToken();
+                LOG.debug("Login with app id, secret and token, all APIs accessible");
+            }
+        }
+        return facebook;
+    }
+
+    public FacebookConfiguration copy() throws CloneNotSupportedException {
+        final FacebookConfiguration copy = (FacebookConfiguration) clone();
+        // do not copy facebook instance!!!
+        copy.facebook = null;
+        return copy;
+    }
+
+    public String getOAuthAccessToken() {
+        return oAuthAccessToken;
+    }
+
+    public void setOAuthAccessToken(String oAuthAccessToken) {
+        this.oAuthAccessToken = oAuthAccessToken;
+    }
+
+    public String getOAuthAccessTokenURL() {
+        return oAuthAccessTokenURL;
+    }
+
+    public void setOAuthAccessTokenURL(String oAuthAccessTokenURL) {
+        this.oAuthAccessTokenURL = oAuthAccessTokenURL;
+    }
+
+    public String getOAuthAppId() {
+        return oAuthAppId;
+    }
+
+    public void setOAuthAppId(String oAuthAppId) {
+        this.oAuthAppId = oAuthAppId;
+    }
+
+    public String getOAuthAppSecret() {
+        return oAuthAppSecret;
+    }
+
+    public void setOAuthAppSecret(String oAuthAppSecret) {
+        this.oAuthAppSecret = oAuthAppSecret;
+    }
+
+    public String getOAuthAuthorizationURL() {
+        return oAuthAuthorizationURL;
+    }
+
+    public void setOAuthAuthorizationURL(String oAuthAuthorizationURL) {
+        this.oAuthAuthorizationURL = oAuthAuthorizationURL;
+    }
+
+    public String getClientURL() {
+        return clientURL;
+    }
+
+    public void setClientURL(String clientURL) {
+        this.clientURL = clientURL;
+    }
+
+    public String getClientVersion() {
+        return clientVersion;
+    }
+
+    public void setClientVersion(String clientVersion) {
+        this.clientVersion = clientVersion;
+    }
+
+    public Boolean getDebugEnabled() {
+        return debugEnabled;
+    }
+
+    public void setDebugEnabled(Boolean debugEnabled) {
+        this.debugEnabled = debugEnabled;
+    }
+
+    public Boolean getGzipEnabled() {
+        return gzipEnabled;
+    }
+
+    public void setGzipEnabled(Boolean gzipEnabled) {
+        this.gzipEnabled = gzipEnabled;
+    }
+
+    public Integer getHttpConnectionTimeout() {
+        return httpConnectionTimeout;
+    }
+
+    public void setHttpConnectionTimeout(Integer httpConnectionTimeout) {
+        this.httpConnectionTimeout = httpConnectionTimeout;
+    }
+
+    public Integer getHttpDefaultMaxPerRoute() {
+        return httpDefaultMaxPerRoute;
+    }
+
+    public void setHttpDefaultMaxPerRoute(Integer httpDefaultMaxPerRoute) {
+        this.httpDefaultMaxPerRoute = httpDefaultMaxPerRoute;
+    }
+
+    public Integer getHttpMaxTotalConnections() {
+        return httpMaxTotalConnections;
+    }
+
+    public void setHttpMaxTotalConnections(Integer httpMaxTotalConnections) {
+        this.httpMaxTotalConnections = httpMaxTotalConnections;
+    }
+
+    public String getHttpProxyHost() {
+        return httpProxyHost;
+    }
+
+    public void setHttpProxyHost(String httpProxyHost) {
+        this.httpProxyHost = httpProxyHost;
+    }
+
+    public String getHttpProxyPassword() {
+        return httpProxyPassword;
+    }
+
+    public void setHttpProxyPassword(String httpProxyPassword) {
+        this.httpProxyPassword = httpProxyPassword;
+    }
+
+    public Integer getHttpProxyPort() {
+        return httpProxyPort;
+    }
+
+    public void setHttpProxyPort(Integer httpProxyPort) {
+        this.httpProxyPort = httpProxyPort;
+    }
+
+    public String getHttpProxyUser() {
+        return httpProxyUser;
+    }
+
+    public void setHttpProxyUser(String httpProxyUser) {
+        this.httpProxyUser = httpProxyUser;
+    }
+
+    public Integer getHttpReadTimeout() {
+        return httpReadTimeout;
+    }
+
+    public void setHttpReadTimeout(Integer httpReadTimeout) {
+        this.httpReadTimeout = httpReadTimeout;
+    }
+
+    public Integer getHttpRetryCount() {
+        return httpRetryCount;
+    }
+
+    public void setHttpRetryCount(Integer httpRetryCount) {
+        this.httpRetryCount = httpRetryCount;
+    }
+
+    public Integer getHttpRetryIntervalSeconds() {
+        return httpRetryIntervalSeconds;
+    }
+
+    public void setHttpRetryIntervalSeconds(Integer httpRetryIntervalSeconds) {
+        this.httpRetryIntervalSeconds = httpRetryIntervalSeconds;
+    }
+
+    public Integer getHttpStreamingReadTimeout() {
+        return httpStreamingReadTimeout;
+    }
+
+    public void setHttpStreamingReadTimeout(Integer httpStreamingReadTimeout) {
+        this.httpStreamingReadTimeout = httpStreamingReadTimeout;
+    }
+
+    public Boolean getJsonStoreEnabled() {
+        return jsonStoreEnabled;
+    }
+
+    public void setJsonStoreEnabled(Boolean jsonStoreEnabled) {
+        this.jsonStoreEnabled = jsonStoreEnabled;
+    }
+
+    public Boolean getMbeanEnabled() {
+        return mbeanEnabled;
+    }
+
+    public void setMbeanEnabled(Boolean mbeanEnabled) {
+        this.mbeanEnabled = mbeanEnabled;
+    }
+
+    public String getOAuthPermissions() {
+        return oAuthPermissions;
+    }
+
+    public void setOAuthPermissions(String oAuthPermissions) {
+        this.oAuthPermissions = oAuthPermissions;
+    }
+
+    public Boolean getPrettyDebugEnabled() {
+        return prettyDebugEnabled;
+    }
+
+    public void setPrettyDebugEnabled(Boolean prettyDebugEnabled) {
+        this.prettyDebugEnabled = prettyDebugEnabled;
+    }
+
+    public String getRestBaseURL() {
+        return restBaseURL;
+    }
+
+    public void setRestBaseURL(String restBaseURL) {
+        this.restBaseURL = restBaseURL;
+    }
+
+    public Boolean getUseSSL() {
+        return useSSL;
+    }
+
+    public void setUseSSL(Boolean useSSL) {
+        this.useSSL = useSSL;
+    }
+
+    public String getVideoBaseURL() {
+        return videoBaseURL;
+    }
+
+    public void setVideoBaseURL(String videoBaseURL) {
+        this.videoBaseURL = videoBaseURL;
+    }
+
+    public void validate() {
+        if ((oAuthAppId == null || oAuthAppId.isEmpty())
+            || (oAuthAppSecret == null || oAuthAppSecret.isEmpty())) {
+            throw new IllegalArgumentException("Missing required properties oAuthAppId, oAuthAppSecret");
+        }
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java
new file mode 100644
index 0000000..1705630
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookEndpointConfiguration.java
@@ -0,0 +1,706 @@
+/**
+ * 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.facebook.config;
+
+import java.lang.reflect.Field;
+import java.net.URL;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+import org.apache.camel.component.facebook.FacebookConstants;
+import org.apache.camel.spi.UriParam;
+import org.apache.camel.spi.UriParams;
+import org.apache.camel.util.ObjectHelper;
+
+import facebook4j.*;
+
+@UriParams
+public class FacebookEndpointConfiguration extends FacebookConfiguration {
+
+    // property name for Exchange 'In' message body
+    @UriParam
+    private String inBody;
+
+    @UriParam
+    private URL achievementURL;
+    @UriParam
+    private AlbumCreate albumCreate;
+    @UriParam
+    private String albumId;
+    @UriParam
+    private Boolean allowNewOptions;
+    @UriParam
+    private String appId;
+    @UriParam
+    private GeoLocation center;
+    @UriParam
+    private CheckinCreate checkinCreate;
+    @UriParam
+    private String checkinId;
+    @UriParam
+    private String commentId;
+    @UriParam
+    private String description;
+    @UriParam
+    private Integer distance;
+    @UriParam
+    private String domainId;
+    @UriParam
+    private String domainName;
+    @UriParam
+    private List<String> domainNames;
+    @UriParam
+    private String eventId;
+    @UriParam
+    private EventUpdate eventUpdate;
+    @UriParam
+    private String friendId;
+    @UriParam
+    private String friendUserId;
+    @UriParam
+    private String friendlistId;
+    @UriParam
+    private String friendlistName;
+    @UriParam
+    private String groupId;
+    @UriParam
+    private List<String> ids;
+    @UriParam
+    private Boolean includeRead;
+    @UriParam
+    private URL link;
+    @UriParam
+    private String linkId;
+    @UriParam
+    private Locale locale;
+    @UriParam
+    private String message;
+    @UriParam
+    private String messageId;
+    @UriParam
+    private String metric;
+    @UriParam
+    private String name;
+    @UriParam
+    private Boolean noStory;
+    @UriParam
+    private String noteId;
+    @UriParam
+    private String notificationId;
+    @UriParam
+    private String objectId;
+    @UriParam
+    private String optionDescription;
+    @UriParam
+    private List<String> options;
+    @UriParam
+    private String permissionName;
+    @UriParam
+    private String permissions;
+    @UriParam
+    private String photoId;
+    @UriParam
+    private String place;
+    @UriParam
+    private String placeId;
+    @UriParam
+    private String postId;
+    @UriParam
+    private PostUpdate postUpdate;
+    @UriParam
+    private Map queries;
+    @UriParam
+    private String query;
+    @UriParam
+    private String question;
+    @UriParam
+    private String questionId;
+    @UriParam
+    private Reading reading;
+    @UriParam
+    private Integer scoreValue;
+    @UriParam
+    private PictureSize size;
+    @UriParam
+    private Media source;
+    @UriParam
+    private String subject;
+    @UriParam
+    private TagUpdate tagUpdate;
+    @UriParam
+    private TestUser testUser1;
+    @UriParam
+    private TestUser testUser2;
+    @UriParam
+    private String testUserId;
+    @UriParam
+    private String title;
+    @UriParam
+    private String toUserId;
+    @UriParam
+    private List<String> toUserIds;
+    @UriParam
+    private String userId1;
+    @UriParam
+    private String userId2;
+    @UriParam
+    private String userId;
+    @UriParam
+    private List<String> userIds;
+    @UriParam
+    private String userLocale;
+    @UriParam
+    private String videoId;
+
+    public String getInBody() {
+        return inBody;
+    }
+
+    public void setInBody(String inBody) {
+        ObjectHelper.notNull(inBody, "inBody");
+        this.inBody = inBody;
+
+        // validate name
+        final List<Field> fields = Arrays.asList(getClass().getDeclaredFields());
+        fields.remove(FacebookConstants.IN_BODY_PROPERTY);
+        if (!fields.contains(inBody)) {
+            throw new IllegalArgumentException("Unknown property " + inBody);
+        }
+    }
+
+    public URL getAchievementURL() {
+        return achievementURL;
+    }
+
+    public void setAchievementURL(URL achievementURL) {
+        this.achievementURL = achievementURL;
+    }
+
+    public AlbumCreate getAlbumCreate() {
+        return albumCreate;
+    }
+
+    public void setAlbumCreate(AlbumCreate albumCreate) {
+        this.albumCreate = albumCreate;
+    }
+
+    public String getAlbumId() {
+        return albumId;
+    }
+
+    public void setAlbumId(String albumId) {
+        this.albumId = albumId;
+    }
+
+    public Boolean isAllowNewOptions() {
+        return allowNewOptions;
+    }
+
+    public void setAllowNewOptions(Boolean allowNewOptions) {
+        this.allowNewOptions = allowNewOptions;
+    }
+
+    public String getoAuthAppId() {
+        return appId;
+    }
+
+    public void setoAuthAppId(String appId) {
+        this.appId = appId;
+    }
+
+    public GeoLocation getCenter() {
+        return center;
+    }
+
+    public void setCenter(GeoLocation center) {
+        this.center = center;
+    }
+
+    public CheckinCreate getCheckinCreate() {
+        return checkinCreate;
+    }
+
+    public void setCheckinCreate(CheckinCreate checkinCreate) {
+        this.checkinCreate = checkinCreate;
+    }
+
+    public String getCheckinId() {
+        return checkinId;
+    }
+
+    public void setCheckinId(String checkinId) {
+        this.checkinId = checkinId;
+    }
+
+    public String getCommentId() {
+        return commentId;
+    }
+
+    public void setCommentId(String commentId) {
+        this.commentId = commentId;
+    }
+
+    public String getDescription() {
+        return description;
+    }
+
+    public void setDescription(String description) {
+        this.description = description;
+    }
+
+    public Integer getDistance() {
+        return distance;
+    }
+
+    public void setDistance(Integer distance) {
+        this.distance = distance;
+    }
+
+    public String getDomainId() {
+        return domainId;
+    }
+
+    public void setDomainId(String domainId) {
+        this.domainId = domainId;
+    }
+
+    public String getDomainName() {
+        return domainName;
+    }
+
+    public void setDomainName(String domainName) {
+        this.domainName = domainName;
+    }
+
+    public List<String> getDomainNames() {
+        return domainNames;
+    }
+
+    public void setDomainNames(List<String> domainNames) {
+        this.domainNames = domainNames;
+    }
+
+    public String getEventId() {
+        return eventId;
+    }
+
+    public void setEventId(String eventId) {
+        this.eventId = eventId;
+    }
+
+    public EventUpdate getEventUpdate() {
+        return eventUpdate;
+    }
+
+    public void setEventUpdate(EventUpdate eventUpdate) {
+        this.eventUpdate = eventUpdate;
+    }
+
+    public String getFriendId() {
+        return friendId;
+    }
+
+    public void setFriendId(String friendId) {
+        this.friendId = friendId;
+    }
+
+    public String getFriendUserId() {
+        return friendUserId;
+    }
+
+    public void setFriendUserId(String friendUserId) {
+        this.friendUserId = friendUserId;
+    }
+
+    public String getFriendlistId() {
+        return friendlistId;
+    }
+
+    public void setFriendlistId(String friendlistId) {
+        this.friendlistId = friendlistId;
+    }
+
+    public String getFriendlistName() {
+        return friendlistName;
+    }
+
+    public void setFriendlistName(String friendlistName) {
+        this.friendlistName = friendlistName;
+    }
+
+    public String getGroupId() {
+        return groupId;
+    }
+
+    public void setGroupId(String groupId) {
+        this.groupId = groupId;
+    }
+
+    public List<String> getIds() {
+        return ids;
+    }
+
+    public void setIds(List<String> ids) {
+        this.ids = ids;
+    }
+
+    public Boolean isIncludeRead() {
+        return includeRead;
+    }
+
+    public void setIncludeRead(Boolean includeRead) {
+        this.includeRead = includeRead;
+    }
+
+    public URL getLink() {
+        return link;
+    }
+
+    public void setLink(URL link) {
+        this.link = link;
+    }
+
+    public String getLinkId() {
+        return linkId;
+    }
+
+    public void setLinkId(String linkId) {
+        this.linkId = linkId;
+    }
+
+    public Locale getLocale() {
+        return locale;
+    }
+
+    public void setLocale(Locale locale) {
+        this.locale = locale;
+    }
+
+    public String getMessage() {
+        return message;
+    }
+
+    public void setMessage(String message) {
+        this.message = message;
+    }
+
+    public String getMessageId() {
+        return messageId;
+    }
+
+    public void setMessageId(String messageId) {
+        this.messageId = messageId;
+    }
+
+    public String getMetric() {
+        return metric;
+    }
+
+    public void setMetric(String metric) {
+        this.metric = metric;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    public Boolean isNoStory() {
+        return noStory;
+    }
+
+    public void setNoStory(Boolean noStory) {
+        this.noStory = noStory;
+    }
+
+    public String getNoteId() {
+        return noteId;
+    }
+
+    public void setNoteId(String noteId) {
+        this.noteId = noteId;
+    }
+
+    public String getNotificationId() {
+        return notificationId;
+    }
+
+    public void setNotificationId(String notificationId) {
+        this.notificationId = notificationId;
+    }
+
+    public String getObjectId() {
+        return objectId;
+    }
+
+    public void setObjectId(String objectId) {
+        this.objectId = objectId;
+    }
+
+    public String getOptionDescription() {
+        return optionDescription;
+    }
+
+    public void setOptionDescription(String optionDescription) {
+        this.optionDescription = optionDescription;
+    }
+
+    public List<String> getOptions() {
+        return options;
+    }
+
+    public void setOptions(List<String> options) {
+        this.options = options;
+    }
+
+    public String getPermissionName() {
+        return permissionName;
+    }
+
+    public void setPermissionName(String permissionName) {
+        this.permissionName = permissionName;
+    }
+
+    public String getoAuthPermissions() {
+        return permissions;
+    }
+
+    public void setoAuthPermissions(String permissions) {
+        this.permissions = permissions;
+    }
+
+    public String getPhotoId() {
+        return photoId;
+    }
+
+    public void setPhotoId(String photoId) {
+        this.photoId = photoId;
+    }
+
+    public String getPlace() {
+        return place;
+    }
+
+    public void setPlace(String place) {
+        this.place = place;
+    }
+
+    public String getPlaceId() {
+        return placeId;
+    }
+
+    public void setPlaceId(String placeId) {
+        this.placeId = placeId;
+    }
+
+    public String getPostId() {
+        return postId;
+    }
+
+    public void setPostId(String postId) {
+        this.postId = postId;
+    }
+
+    public PostUpdate getPostUpdate() {
+        return postUpdate;
+    }
+
+    public void setPostUpdate(PostUpdate postUpdate) {
+        this.postUpdate = postUpdate;
+    }
+
+    public Map getQueries() {
+        return queries;
+    }
+
+    public void setQueries(Map queries) {
+        this.queries = queries;
+    }
+
+    public String getQuery() {
+        return query;
+    }
+
+    public void setQuery(String query) {
+        this.query = query;
+    }
+
+    public String getQuestion() {
+        return question;
+    }
+
+    public void setQuestion(String question) {
+        this.question = question;
+    }
+
+    public String getQuestionId() {
+        return questionId;
+    }
+
+    public void setQuestionId(String questionId) {
+        this.questionId = questionId;
+    }
+
+    public Reading getReading() {
+        return reading;
+    }
+
+    public void setReading(Reading reading) {
+        this.reading = reading;
+    }
+
+    public Integer getScoreValue() {
+        return scoreValue;
+    }
+
+    public void setScoreValue(Integer scoreValue) {
+        this.scoreValue = scoreValue;
+    }
+
+    public PictureSize getSize() {
+        return size;
+    }
+
+    public void setSize(PictureSize size) {
+        this.size = size;
+    }
+
+    public Media getSource() {
+        return source;
+    }
+
+    public void setSource(Media source) {
+        this.source = source;
+    }
+
+    public String getSubject() {
+        return subject;
+    }
+
+    public void setSubject(String subject) {
+        this.subject = subject;
+    }
+
+    public TagUpdate getTagUpdate() {
+        return tagUpdate;
+    }
+
+    public void setTagUpdate(TagUpdate tagUpdate) {
+        this.tagUpdate = tagUpdate;
+    }
+
+    public TestUser getTestUser1() {
+        return testUser1;
+    }
+
+    public void setTestUser1(TestUser testUser1) {
+        this.testUser1 = testUser1;
+    }
+
+    public TestUser getTestUser2() {
+        return testUser2;
+    }
+
+    public void setTestUser2(TestUser testUser2) {
+        this.testUser2 = testUser2;
+    }
+
+    public String getTestUserId() {
+        return testUserId;
+    }
+
+    public void setTestUserId(String testUserId) {
+        this.testUserId = testUserId;
+    }
+
+    public String getTitle() {
+        return title;
+    }
+
+    public void setTitle(String title) {
+        this.title = title;
+    }
+
+    public String getToUserId() {
+        return toUserId;
+    }
+
+    public void setToUserId(String toUserId) {
+        this.toUserId = toUserId;
+    }
+
+    public List<String> getToUserIds() {
+        return toUserIds;
+    }
+
+    public void setToUserIds(List<String> toUserIds) {
+        this.toUserIds = toUserIds;
+    }
+
+    public String getUserId1() {
+        return userId1;
+    }
+
+    public void setUserId1(String userId1) {
+        this.userId1 = userId1;
+    }
+
+    public String getUserId2() {
+        return userId2;
+    }
+
+    public void setUserId2(String userId2) {
+        this.userId2 = userId2;
+    }
+
+    public String getUserId() {
+        return userId;
+    }
+
+    public void setUserId(String userId) {
+        this.userId = userId;
+    }
+
+    public List<String> getUserIds() {
+        return userIds;
+    }
+
+    public void setUserIds(List<String> userIds) {
+        this.userIds = userIds;
+    }
+
+    public String getUserLocale() {
+        return userLocale;
+    }
+
+    public void setUserLocale(String userLocale) {
+        this.userLocale = userLocale;
+    }
+
+    public String getVideoId() {
+        return videoId;
+    }
+
+    public void setVideoId(String videoId) {
+        this.videoId = videoId;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookNameStyle.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookNameStyle.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookNameStyle.java
new file mode 100644
index 0000000..238582b
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/config/FacebookNameStyle.java
@@ -0,0 +1,26 @@
+/**
+ * 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.facebook.config;
+
+/**
+ * Constants for method name style.
+ */
+public enum FacebookNameStyle {
+
+    EXACT, GET, SEARCH, GET_AND_SEARCH;
+
+}


[2/4] CAMEL-6676 Added camel-facebook component with thanks for Dhiraj

Posted by ni...@apache.org.
http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java
new file mode 100644
index 0000000..02ef2fd
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsType.java
@@ -0,0 +1,572 @@
+/**
+ * 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.facebook.data;
+
+import java.lang.reflect.Method;
+import java.net.URL;
+import java.util.*;
+import org.apache.camel.component.facebook.FacebookConstants;
+
+import facebook4j.*;
+import facebook4j.internal.org.json.JSONArray;
+
+/**
+ * Enum for Facebook4J *Method interfaces.
+ * The methods are ordered by the number and nature of arguments.
+ */
+public enum FacebookMethodsType {
+
+    // AccountMethods
+    GET_ACCOUNTS(ResponseList.class, "getAccounts"),
+    GET_ACCOUNTS_WITH_OPTIONS(ResponseList.class, "getAccounts", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GET_ACCOUNTS_WITH_ID(ResponseList.class, "getAccounts", String.class, "userId"),
+    GET_ACCOUNTS_WITH_ID_OPTIONS(ResponseList.class, "getAccounts", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // ActivityMethods
+    GETACTIVITIES(ResponseList.class, "getActivities"),
+    GETACTIVITIES_WITH_OPTIONS(ResponseList.class, "getActivities", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETACTIVITIES_WITH_ID(ResponseList.class, "getActivities", String.class, "userId"),
+    GETACTIVITIES_WITH_ID_OPTIONS(ResponseList.class, "getActivities", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // AlbumMethods
+    ADDALBUMPHOTO(String.class, "addAlbumPhoto", String.class, "albumId", Media.class, "source"),
+    ADDALBUMPHOTO_WITH_MEDIA(String.class, "addAlbumPhoto", String.class, "albumId", Media.class, "source", String.class, "message"),
+    COMMENTALBUM(String.class, "commentAlbum", String.class, "albumId", String.class, "message"),
+    CREATEALBUM(String.class, "createAlbum", AlbumCreate.class, "albumCreate"),
+    CREATEALBUM_WITH_ID(String.class, "createAlbum", String.class, "userId", AlbumCreate.class, "albumCreate"),
+    GETALBUM(Album.class,  "getAlbum", String.class, "albumId"),
+    GETALBUM_WITH_OPTIONS(Album.class,  "getAlbum", String.class, "albumId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETALBUMCOMMENTS(ResponseList.class, "getAlbumComments", String.class, "albumId"),
+    GETALBUMCOMMENTS_WITH_OPTIONS(ResponseList.class, "getAlbumComments", String.class, "albumId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETALBUMCOVERPHOTO(URL.class, "getAlbumCoverPhoto", String.class, "albumId"),
+    GETALBUMLIKES(ResponseList.class, "getAlbumLikes", String.class, "albumId"),
+    GETALBUMLIKES_WITH_OPTIONS(ResponseList.class, "getAlbumLikes", String.class, "albumId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETALBUMPHOTOS(ResponseList.class, "getAlbumPhotos", String.class, "albumId"),
+    GETALBUMPHOTOS_WITH_OPTIONS(ResponseList.class, "getAlbumPhotos", String.class, "albumId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETALBUMS(ResponseList.class, "getAlbums"),
+    GETALBUMS_WITH_OPTIONS(ResponseList.class, "getAlbums", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETALBUMS_WITH_ID(ResponseList.class, "getAlbums", String.class, "userId"),
+    GETALBUMS_WITH_ID_OPTIONS(ResponseList.class, "getAlbums", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKEALBUM(boolean.class, "likeAlbum", String.class, "albumId"),
+    UNLIKEALBUM(boolean.class, "unlikeAlbum", String.class, "albumId"),
+
+    // CheckinMethods
+    CHECKIN(String.class, "checkin", CheckinCreate.class, "checkinCreate"),
+    CHECKIN_WITH_ID(String.class, "checkin", String.class, "userId", CheckinCreate.class, "checkinCreate"),
+    COMMENTCHECKIN(String.class, "commentCheckin", String.class, "checkinId", String.class, "message"),
+    GETCHECKIN(Checkin.class, "getCheckin", String.class, "checkinId"),
+    GETCHECKIN_WITH_OPTIONS(Checkin.class, "getCheckin", String.class, "checkinId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETCHECKINCOMMENTS(ResponseList.class, "getCheckinComments", String.class, "checkinId"),
+    GETCHECKINCOMMENTS_WITH_OPTIONS(ResponseList.class, "getCheckinComments", String.class, "checkinId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETCHECKINLIKES(ResponseList.class, "getCheckinLikes", String.class, "checkinId"),
+    GETCHECKINLIKES_WITH_OPTIONS(ResponseList.class, "getCheckinLikes", String.class, "checkinId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETCHECKINS(ResponseList.class, "getCheckins"),
+    GETCHECKINS_WITH_OPTIONS(ResponseList.class, "getCheckins", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETCHECKINS_WITH_ID(ResponseList.class, "getCheckins", String.class, "userId"),
+    GETCHECKINS_WITH_ID_OPTIONS(ResponseList.class, "getCheckins", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKECHECKIN(boolean.class, "likeCheckin", String.class, "checkinId"),
+    UNLIKECHECKIN(boolean.class, "unlikeCheckin", String.class, "checkinId"),
+
+    // CommentMethods
+    DELETECOMMENT(boolean.class, "deleteComment", String.class, "commentId"),
+    GETCOMMENT(Comment.class, "getComment", String.class, "commentId"),
+    GETCOMMENTLIKES(ResponseList.class, "getCommentLikes", String.class, "commentId"),
+    GETCOMMENTLIKES_WITH_OPTIONS(ResponseList.class, "getCommentLikes", String.class, "commentId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKECOMMENT(boolean.class, "likeComment", String.class, "commentId"),
+    UNLIKECOMMENT(Boolean.class, "unlikeComment", String.class, "commentId"),
+
+    // DomainMethods
+    GETDOMAIN(Domain.class, "getDomain", String.class, "domainId"),
+    GETDOMAINBYNAME(Domain.class, "getDomainByName", String.class, "domainName"),
+    GETDOMAINSBYNAME_WITH_DOMAINS(List.class, "getDomainsByName", new String[0].getClass(), "domainNames"),
+
+    // EventMethods
+    CREATEEVENT(String.class, "createEvent", EventUpdate.class, "eventUpdate"),
+    CREATEEVENT_WITH_ID(String.class, "createEvent", String.class, "userId", EventUpdate.class, "eventUpdate"),
+    DELETEEVENT(Boolean.class,  "deleteEvent", String.class, "eventId"),
+    DELETEEVENTPICTURE(Boolean.class,  "deleteEventPicture", String.class, "eventId"),
+    EDITEVENT(Boolean.class,  "editEvent", String.class, "eventId", EventUpdate.class, "eventUpdate"),
+    GETEVENT(Event.class,  "getEvent", String.class, "eventId"),
+    GETEVENT_WITH_OPTIONS(Event.class,  "getEvent", String.class, "eventId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETEVENTFEED(ResponseList.class, "getEventFeed", String.class, "eventId"),
+    GETEVENTFEED_WITH_OPTIONS(ResponseList.class, "getEventFeed", String.class, "eventId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETEVENTPHOTOS(ResponseList.class, "getEventPhotos", String.class, "eventId"),
+    GETEVENTPHOTOS_WITH_OPTIONS(ResponseList.class, "getEventPhotos", String.class, "eventId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETEVENTPICTUREURL(URL.class,  "getEventPictureURL", String.class, "eventId"),
+    GETEVENTPICTUREURL_WITH_PICTURESIZE(URL.class,  "getEventPictureURL", String.class, "eventId", PictureSize.class, "size"),
+    GETEVENTS(ResponseList.class, "getEvents"),
+    GETEVENTS_WITH_OPTIONS(ResponseList.class, "getEvents", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETEVENTS_WITH_ID(ResponseList.class, "getEvents", String.class, "userId"),
+    GETEVENTS_WITH_ID_OPTIONS(ResponseList.class, "getEvents", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETEVENTVIDEOS(ResponseList.class, "getEventVideos", String.class, "eventId"),
+    GETEVENTVIDEOS_WITH_OPTIONS(ResponseList.class, "getEventVideos", String.class, "eventId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETRSVPSTATUSASINVITED(ResponseList.class, "getRSVPStatusAsInvited", String.class, "eventId"),
+    GETRSVPSTATUSASINVITED_WITH_ID(ResponseList.class, "getRSVPStatusAsInvited", String.class, "eventId", String.class, "userId"),
+    GETRSVPSTATUSASNOREPLY(ResponseList.class, "getRSVPStatusAsNoreply", String.class, "eventId"),
+    GETRSVPSTATUSASNOREPLY_WITH_ID(ResponseList.class, "getRSVPStatusAsNoreply", String.class, "eventId", String.class, "userId"),
+    GETRSVPSTATUSINATTENDING(ResponseList.class, "getRSVPStatusInAttending", String.class, "eventId"),
+    GETRSVPSTATUSINATTENDING_WITH_ID(ResponseList.class, "getRSVPStatusInAttending", String.class, "eventId", String.class, "userId"),
+    GETRSVPSTATUSINDECLINED(ResponseList.class, "getRSVPStatusInDeclined", String.class, "eventId"),
+    GETRSVPSTATUSINDECLINED_WITH_ID(ResponseList.class, "getRSVPStatusInDeclined", String.class, "eventId", String.class, "userId"),
+    GETRSVPSTATUSINMAYBE(ResponseList.class, "getRSVPStatusInMaybe", String.class, "eventId"),
+    GETRSVPSTATUSINMAYBE_WITH_ID(ResponseList.class, "getRSVPStatusInMaybe", String.class, "eventId", String.class, "userId"),
+    INVITETOEVENT(Boolean.class,  "inviteToEvent", String.class, "eventId", String.class, "userId"),
+    INVITETOEVENT_WITH_IDS(Boolean.class,  "inviteToEvent", String.class, "eventId", new String[0].getClass(), "userIds"),
+    POSTEVENTFEED_WITH_POSTUPDATE(String.class, "postEventFeed", String.class, "eventId", PostUpdate.class, "postUpdate"),
+    POSTEVENTLINK_WITH_LINK(String.class, "postEventLink", String.class, "eventId", URL.class , "link"),
+    POSTEVENTLINK_WITH_LINK_MSG(String.class, "postEventLink", String.class, "eventId", URL.class , "link", String.class, "message"),
+    POSTEVENTPHOTO_WITH_MEDIA(String.class, "postEventPhoto", String.class, "eventId", Media.class, "source"),
+    POSTEVENTPHOTO_WITH_MEDIA_MSG(String.class, "postEventPhoto", String.class, "eventId", Media.class, "source", String.class, "message"),
+    POSTEVENTSTATUSMESSAGE_WITH_MSG(String.class, "postEventStatusMessage", String.class, "eventId", String.class, "message"),
+    POSTEVENTVIDEO_WITH_MEDIA(String.class, "postEventVideo", String.class, "eventId", Media.class, "source"),
+    POSTEVENTVIDEO_WITH_MEDIA_TITLE_DESC(String.class, "postEventVideo", String.class, "eventId", Media.class, "source", String.class, "title", String.class, "description"),
+    RSVPEVENTASATTENDING(Boolean.class,  "rsvpEventAsAttending", String.class, "eventId"),
+    RSVPEVENTASDECLINED(Boolean.class,  "rsvpEventAsDeclined", String.class, "eventId"),
+    RSVPEVENTASMAYBE(Boolean.class,  "rsvpEventAsMaybe", String.class, "eventId"),
+    UNINVITEFROMEVENT(Boolean.class,  "uninviteFromEvent", String.class, "eventId", String.class, "userId"),
+    UPDATEEVENTPICTURE(Boolean.class,  "updateEventPicture", String.class, "eventId", Media.class, "source"),
+
+    // FamilyMethods
+    GETFAMILY(ResponseList.class, "getFamily"),
+    GETFAMILY_WITH_OPTIONS(ResponseList.class, "getFamily", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFAMILY_WITH_ID(ResponseList.class, "getFamily", String.class, "userId"),
+    GETFAMILY_WITH_ID_OPTIONS(ResponseList.class, "getFamily", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // FavouriteMethods
+    GETBOOKS(ResponseList.class, "getBooks"),
+    GETBOOKS_WITH_OPTIONS(ResponseList.class, "getBooks", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETBOOKS_WITH_ID(ResponseList.class, "getBooks", String.class, "userId"),
+    GETBOOKS_WITH_ID_OPTIONS(ResponseList.class, "getBooks", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETGAMES(ResponseList.class, "getGames"),
+    GETGAMES_WITH_OPTIONS(ResponseList.class, "getGames", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETGAMES_WITH_ID(ResponseList.class, "getGames", String.class, "userId"),
+    GETGAMES_WITH_ID_OPTIONS(ResponseList.class, "getGames", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETINTERESTS(ResponseList.class, "getInterests"),
+    GETINTERESTS_WITH_OPTIONS(ResponseList.class, "getInterests", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETINTERESTS_WITH_ID(ResponseList.class, "getInterests", String.class, "userId"),
+    GETINTERESTS_WITH_ID_OPTIONS(ResponseList.class, "getInterests", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETMOVIES(ResponseList.class, "getMovies"),
+    GETMOVIES_WITH_OPTIONS(ResponseList.class, "getMovies", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETMOVIES_WITH_ID(ResponseList.class, "getMovies", String.class, "userId"),
+    GETMOVIES_WITH_ID_OPTIONS(ResponseList.class, "getMovies", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETMUSIC(ResponseList.class, "getMusic"),
+    GETMUSIC_WITH_OPTIONS(ResponseList.class, "getMusic", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETMUSIC_WITH_ID(ResponseList.class, "getMusic", String.class, "userId"),
+    GETMUSIC_WITH_ID_OPTIONS(ResponseList.class, "getMusic", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETTELEVISION(ResponseList.class, "getTelevision"),
+    GETTELEVISION_WITH_OPTIONS(ResponseList.class, "getTelevision", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETTELEVISION_WITH_ID(ResponseList.class, "getTelevision", String.class, "userId"),
+    GETTELEVISION_WITH_ID_OPTIONS(ResponseList.class, "getTelevision", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // FQLMethods
+    EXECUTEFQL(JSONArray.class, "executeFQL", String.class, "query"),
+    EXECUTEFQL_WITH_LOCALE(JSONArray.class, "executeFQL", String.class, "query", Locale.class, " locale"),
+    EXECUTEMULTIFQL(Map.class, "executeMultiFQL", Map.class, "queries"),
+    EXECUTEMULTIFQL_WITH_LOCALE(Map.class, "executeMultiFQL", Map.class, "queries", Locale.class, "locale"),
+
+    // FriendMethods
+    ADDFRIENDLISTMEMBER(Boolean.class, "addFriendlistMember", String.class, "friendlistId", String.class, "userId"),
+    CREATEFRIENDLIST(String.class, "createFriendlist", String.class, "friendlistName"),
+    CREATEFRIENDLIST_WITH_ID(String.class, "createFriendlist", String.class, "userId", String.class, "friendlistName"),
+    DELETEFRIENDLIST(Boolean.class, "deleteFriendlist", String.class, "friendlistId"),
+    GETBELONGSFRIEND(ResponseList.class, "getBelongsFriend", String.class, "friendId"),
+    GETBELONGSFRIEND_WITH_OPTIONS(ResponseList.class, "getBelongsFriend", String.class, "friendId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETBELONGSFRIEND_WITH_ID(ResponseList.class, "getBelongsFriend", String.class, "userId", String.class, "friendId"),
+    GETBELONGSFRIEND_WITH_ID_OPTIONS(ResponseList.class, "getBelongsFriend", String.class, "userId", String.class, "friendId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFRIENDLIST(Friendlist.class, "getFriendlist", String.class, "friendlistId"),
+    GETFRIENDLIST_WITH_OPTIONS(Friendlist.class, "getFriendlist", String.class, "friendlistId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFRIENDLISTMEMBERS(ResponseList.class, "getFriendlistMembers", String.class, "friendlistId"),
+    GETFRIENDLISTS(ResponseList.class, "getFriendlists"),
+    GETFRIENDLISTS_WITH_OPTIONS(ResponseList.class, "getFriendlists", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFRIENDLISTS_WITH_ID(ResponseList.class, "getFriendlists", String.class, "userId"),
+    GETFRIENDLISTS_WITH_ID_OPTIONS(ResponseList.class, "getFriendlists", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFRIENDREQUESTS(ResponseList.class, "getFriendRequests"),
+    GETFRIENDREQUESTS_WITH_OPTIONS(ResponseList.class, "getFriendRequests", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFRIENDREQUESTS_WITH_ID(ResponseList.class, "getFriendRequests", String.class, "userId"),
+    GETFRIENDREQUESTS_WITH_ID_OPTIONS(ResponseList.class, "getFriendRequests", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFRIENDS(ResponseList.class, "getFriends"),
+    GETFRIENDS_WITH_OPTIONS(ResponseList.class, "getFriends", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFRIENDS_WITH_ID(ResponseList.class, "getFriends", String.class, "userId"),
+    GETFRIENDS_WITH_ID_OPTIONS(ResponseList.class, "getFriends", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETMUTUALFRIENDS(ResponseList.class, "getMutualFriends", String.class, "friendUserId"),
+    GETMUTUALFRIENDS_WITH_OPTIONS(ResponseList.class, "getMutualFriends", String.class, "friendUserId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETMUTUALFRIENDS_WITH_ID(ResponseList.class, "getMutualFriends", String.class, "userId1", String.class, "userId2"),
+    GETMUTUALFRIENDS_WITH_ID_OPTIONS(ResponseList.class, "getMutualFriends", String.class, "userId1", String.class, "userId2", Reading.class, FacebookConstants.READING_PPROPERTY),
+    REMOVEFRIENDLISTMEMBER(Boolean.class, "removeFriendlistMember", String.class, "friendlistId", String.class, "userId"),
+
+    // GameMethods
+    DELETEACHIEVEMENT(Boolean.class, "deleteAchievement", URL.class, "achievementURL"),
+    DELETEACHIEVEMENT_WITH_ID(Boolean.class, "deleteAchievement", String.class, "userId", URL.class , "achievementURL"),
+    DELETESCORE(Boolean.class, "deleteScore"),
+    DELETESCORE_WITH_ID(Boolean.class, "deleteScore", String.class, "userId"),
+    GETACHIEVEMENTS(ResponseList.class, "getAchievements"),
+    GETACHIEVEMENTS_WITH_OPTIONS(ResponseList.class, "getAchievements", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETACHIEVEMENTS_WITH_ID(ResponseList.class, "getAchievements", String.class, "userId"),
+    GETACHIEVEMENTS_WITH_ID_OPTIONS(ResponseList.class, "getAchievements", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETSCORES(ResponseList.class, "getScores"),
+    GETSCORES_WITH_OPTIONS(ResponseList.class, "getScores", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETSCORES_WITH_ID(ResponseList.class, "getScores", String.class, "userId"),
+    GETSCORES_WITH_ID_OPTIONS(ResponseList.class, "getScores", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    POSTACHIEVEMENT(String.class, "postAchievement", URL.class, "achievementURL"),
+    POSTACHIEVEMENT_WITH_ID(String.class, "postAchievement", String.class, "userId", URL.class, "achievementURL"),
+    POSTSCORE(Boolean.class, "postScore", int.class, "scoreValue"),
+    POSTSCORE_WITH_ID(Boolean.class,  "postScore", String.class, "userId", int.class, "scoreValue"),
+
+    // GroupMethods
+    GETGROUP(Group.class,  "getGroup", String.class, "groupId"),
+    GETGROUP_WITH_OPTIONS(Group.class,  "getGroup", String.class, "groupId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETGROUPDOCS(ResponseList.class, "getGroupDocs", String.class, "groupId"),
+    GETGROUPDOCS_WITH_OPTIONS(ResponseList.class, "getGroupDocs", String.class, "groupId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETGROUPFEED(ResponseList.class, "getGroupFeed", String.class, "groupId"),
+    GETGROUPFEED_WITH_OPTIONS(ResponseList.class, "getGroupFeed", String.class, "groupId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETGROUPMEMBERS(ResponseList.class, "getGroupMembers", String.class, "groupId"),
+    GETGROUPMEMBERS_WITH_OPTIONS(ResponseList.class, "getGroupMembers", String.class, "groupId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETGROUPPICTUREURL(URL.class,  "getGroupPictureURL", String.class, "groupId"),
+    GETGROUPS(ResponseList.class, "getGroups"),
+    GETGROUPS_WITH_OPTIONS(ResponseList.class, "getGroups", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETGROUPS_WITH_ID(ResponseList.class, "getGroups", String.class, "userId"),
+    GETGROUPS_WITH_ID_OPTIONS(ResponseList.class, "getGroups", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    POSTGROUPFEED_WITH_POSTUPDATE(String.class, "postGroupFeed", String.class, "groupId", PostUpdate.class, "postUpdate"),
+    POSTGROUPLINK_WITH_LINK(String.class, "postGroupLink", String.class, "groupId", URL.class, "link"),
+    POSTGROUPLINK_WITH_LINK_MSG(String.class, "postGroupLink", String.class, "groupId", URL.class, "link", String.class, "message"),
+    POSTGROUPSTATUSMESSAGE(String.class, "postGroupStatusMessage", String.class, "groupId", String.class, "message"),
+
+    // InsightMethods
+    GETINSIGHTS(ResponseList.class, "getInsights", String.class, "objectId", String.class, "metric"),
+    GETINSIGHTS_WITH_OPTIONS(ResponseList.class, "getInsights", String.class, "objectId", String.class, "metric", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // LikeMethods
+    GETUSERLIKES(ResponseList.class, "getUserLikes"),
+    GETUSERLIKES_WITH_OPTIONS(ResponseList.class, "getUserLikes", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETUSERLIKES_WITH_ID(ResponseList.class, "getUserLikes", String.class, "userId"),
+    GETUSERLIKES_WITH_ID_OPTIONS(ResponseList.class, "getUserLikes", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // LinkMethods
+    COMMENTLINK(String.class, "commentLink", String.class, "linkId", String.class, "message"),
+    GETLINK(Link.class,  "getLink", String.class, "linkId"),
+    GETLINK_WITH_OPTIONS(Link.class,  "getLink", String.class, "linkId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETLINKCOMMENTS(ResponseList.class, "getLinkComments", String.class, "linkId"),
+    GETLINKCOMMENTS_WITH_OPTIONS(ResponseList.class, "getLinkComments", String.class, "linkId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETLINKLIKES(ResponseList.class, "getLinkLikes", String.class, "linkId"),
+    GETLINKLIKES_WITH_OPTIONS(ResponseList.class, "getLinkLikes", String.class, "linkId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKELINK(Boolean.class,  "likeLink", String.class, "linkId"),
+    UNLIKELINK(Boolean.class,  "unlikeLink", String.class, "linkId"),
+
+    // LocationMethods
+    GETLOCATIONS(ResponseList.class, "getLocations"),
+    GETLOCATIONS_WITH_OPTIONS(ResponseList.class, "getLocations", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETLOCATIONS_WITH_ID(ResponseList.class, "getLocations", String.class, "userId"),
+    GETLOCATIONS_WITH_ID_OPTIONS(ResponseList.class, "getLocations", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // MessageMethods
+    GETINBOX(InboxResponseList.class, "getInbox"),
+    GETINBOX_WITH_OPTIONS(InboxResponseList.class, "getInbox", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETINBOX_WITH_ID(InboxResponseList.class, "getInbox", String.class, "userId"),
+    GETINBOX_WITH_ID_OPTIONS(InboxResponseList.class, "getInbox", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETMESSAGE(Message.class,  "getMessage", String.class, "messageId"),
+    GETMESSAGE_WITH_OPTIONS(Message.class,  "getMessage", String.class, "messageId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETOUTBOX(ResponseList.class, "getOutbox"),
+    GETOUTBOX_WITH_OPTIONS(ResponseList.class, "getOutbox", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETOUTBOX_WITH_ID(ResponseList.class, "getOutbox", String.class, "userId"),
+    GETOUTBOX_WITH_ID_OPTIONS(ResponseList.class, "getOutbox", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETUPDATES(ResponseList.class, "getUpdates"),
+    GETUPDATES_WITH_OPTIONS(ResponseList.class, "getUpdates", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETUPDATES_WITH_ID(ResponseList.class, "getUpdates", String.class, "userId"),
+    GETUPDATES_WITH_ID_OPTIONS(ResponseList.class, "getUpdates", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // NoteMethods
+    COMMENTNOTE(String.class, "commentNote", String.class, "noteId", String.class, "message"),
+    CREATENOTE(String.class, "createNote", String.class, "subject", String.class, "message"),
+    CREATENOTE_WITH_ID_MSG(String.class, "createNote", String.class, "userId", String.class, "subject", String.class, "message"),
+    GETNOTE(Note.class,  "getNote", String.class, "noteId"),
+    GETNOTE_WITH_OPTIONS(Note.class,  "getNote", String.class, "noteId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETNOTECOMMENTS(ResponseList.class, "getNoteComments", String.class, "noteId"),
+    GETNOTECOMMENTS_WITH_OPTIONS(ResponseList.class, "getNoteComments", String.class, "noteId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETNOTELIKES(ResponseList.class, "getNoteLikes", String.class, "noteId"),
+    GETNOTELIKES_WITH_OPTIONS(ResponseList.class, "getNoteLikes", String.class, "noteId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETNOTES(ResponseList.class, "getNotes"),
+    GETNOTES_WITH_OPTIONS(ResponseList.class, "getNotes", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETNOTES_WITH_ID(ResponseList.class, "getNotes", String.class, "userId"),
+    GETNOTES_WITH_ID_OPTIONS(ResponseList.class, "getNotes", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKENOTE(Boolean.class,  "likeNote", String.class, "noteId"),
+    UNLIKENOTE(Boolean.class,  "unlikeNote", String.class, "noteId"),
+
+    // NotificationMethods
+    GETNOTIFICATIONS(ResponseList.class, "getNotifications"),
+    GETNOTIFICATIONS_WITH_INCLUDEREAD(ResponseList.class, "getNotifications", boolean.class, "includeRead"),
+    GETNOTIFICATIONS_WITH_OPTIONS(ResponseList.class, "getNotifications", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETNOTIFICATIONS_WITH_OPTIONS_INCLUDEREAD(ResponseList.class, "getNotifications", Reading.class, FacebookConstants.READING_PPROPERTY, boolean.class, "includeRead"),
+    GETNOTIFICATIONS_WITH_ID(ResponseList.class, "getNotifications", String.class, "userId"),
+    GETNOTIFICATIONS_WITH_ID_INCLUDEREAD(ResponseList.class, "getNotifications", String.class, "userId", boolean.class, "includeRead"),
+    GETNOTIFICATIONS_WITH_ID_OPTIONS(ResponseList.class, "getNotifications", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETNOTIFICATIONS_WITH_ID_OPTIONS_INCLUDEREAD(ResponseList.class, "getNotifications", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY, boolean.class, "includeRead"),
+    MARKNOTIFICATIONASREAD(Boolean.class,  "markNotificationAsRead", String.class, "notificationId"),
+
+    // PermissionMethods
+    GETPERMISSIONS(List.class, "getPermissions"),
+    GETPERMISSIONS_WITH_ID(List.class, "getPermissions", String.class, "userId"),
+    REVOKEPERMISSION(Boolean.class,  "revokePermission", String.class, "permissionName"),
+    REVOKEPERMISSION_WITH_ID(Boolean.class,  "revokePermission", String.class, "userId", String.class, "permissionName"),
+
+    // PhotoMethods
+    ADDTAGTOPHOTO(Boolean.class,  "addTagToPhoto", String.class, "photoId", String.class, "toUserId"),
+    ADDTAGTOPHOTO_WITH_IDS(Boolean.class,  "addTagToPhoto", String.class, "photoId", List.class, "toUserIds"),
+    ADDTAGTOPHOTO_WITH_TAGUPDATE(Boolean.class,  "addTagToPhoto", String.class, "photoId", TagUpdate.class, "tagUpdate"),
+    COMMENTPHOTO(String.class, "commentPhoto", String.class, "photoId", String.class, "message"),
+    DELETEPHOTO(Boolean.class,  "deletePhoto", String.class, "photoId"),
+    GETPHOTO(Photo.class,  "getPhoto", String.class, "photoId"),
+    GETPHOTO_WITH_OPTIONS(Photo.class,  "getPhoto", String.class, "photoId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPHOTOCOMMENTS(ResponseList.class, "getPhotoComments", String.class, "photoId"),
+    GETPHOTOCOMMENTS_WITH_OPTIONS(ResponseList.class, "getPhotoComments", String.class, "photoId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPHOTOLIKES(ResponseList.class, "getPhotoLikes", String.class, "photoId"),
+    GETPHOTOLIKES_WITH_OPTIONS(ResponseList.class, "getPhotoLikes", String.class, "photoId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPHOTOS(ResponseList.class, "getPhotos"),
+    GETPHOTOS_WITH_OPTIONS(ResponseList.class, "getPhotos", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPHOTOS_WITH_ID(ResponseList.class, "getPhotos", String.class, "userId"),
+    GETPHOTOS_WITH_ID_OPTIONS(ResponseList.class, "getPhotos", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPHOTOURL(URL.class,  "getPhotoURL", String.class, "photoId"),
+    GETTAGSONPHOTO(ResponseList.class, "getTagsOnPhoto", String.class, "photoId"),
+    GETTAGSONPHOTO_WITH_OPTIONS(ResponseList.class, "getTagsOnPhoto", String.class, "photoId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKEPHOTO(Boolean.class,  "likePhoto", String.class, "photoId"),
+    POSTPHOTO(String.class, "postPhoto", Media.class, "source"),
+    POSTPHOTO_WITH_MSG(String.class, "postPhoto", Media.class, "source", String.class, "message", String.class, "place", boolean.class, "noStory"),
+    POSTPHOTO_WITH_MEDIA(String.class, "postPhoto", String.class, "userId", Media.class, "source"),
+    POSTPHOTO_WITH_MEDIA_MSG(String.class, "postPhoto", String.class, "userId", Media.class, "source", String.class, "message", String.class, "place", boolean.class, "noStory"),
+    UNLIKEPHOTO(Boolean.class,  "unlikePhoto", String.class, "photoId"),
+    UPDATETAGONPHOTO(Boolean.class,  "updateTagOnPhoto", String.class, "photoId", String.class, "toUserId"),
+    UPDATETAGONPHOTO_WITH_TAGUPDATE(Boolean.class,  "updateTagOnPhoto", String.class, "photoId", TagUpdate.class, "tagUpdate"),
+
+    // PokeMethods
+    GETPOKES(ResponseList.class, "getPokes"),
+    GETPOKES_WITH_OPTIONS(ResponseList.class, "getPokes", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPOKES_WITH_ID(ResponseList.class, "getPokes", String.class, "userId"),
+    GETPOKES_WITH_ID_OPTIONS(ResponseList.class, "getPokes", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // PostMethods
+    COMMENTPOST(String.class, "commentPost", String.class, "postId", String.class, "message"),
+    DELETEPOST(Boolean.class,  "deletePost", String.class, "postId"),
+    GETFEED(ResponseList.class, "getFeed"),
+    GETFEED_WITH_OPTIONS(ResponseList.class, "getFeed", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETFEED_WITH_ID(ResponseList.class, "getFeed", String.class, "userId"),
+    GETFEED_WITH_ID_OPTIONS(ResponseList.class, "getFeed", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETHOME(ResponseList.class, "getHome"),
+    GETHOME_WITH_OPTIONS(ResponseList.class, "getHome", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETLINKS(ResponseList.class, "getLinks"),
+    GETLINKS_WITH_OPTIONS(ResponseList.class, "getLinks", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETLINKS_WITH_ID(ResponseList.class, "getLinks", String.class, "userId"),
+    GETLINKS_WITH_ID_OPTIONS(ResponseList.class, "getLinks", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPOST(Post.class,  "getPost", String.class, "postId"),
+    GETPOST_WITH_OPTIONS(Post.class,  "getPost", String.class, "postId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPOSTCOMMENTS(ResponseList.class, "getPostComments", String.class, "postId"),
+    GETPOSTCOMMENTS_WITH_OPTIONS(ResponseList.class, "getPostComments", String.class, "postId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPOSTLIKES(ResponseList.class, "getPostLikes", String.class, "postId"),
+    GETPOSTLIKES_WITH_OPTIONS(ResponseList.class, "getPostLikes", String.class, "postId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPOSTS(ResponseList.class, "getPosts"),
+    GETPOSTS_WITH_OPTIONS(ResponseList.class, "getPosts", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPOSTS_WITH_ID(ResponseList.class, "getPosts", String.class, "userId"),
+    GETPOSTS_WITH_ID_OPTIONS(ResponseList.class, "getPosts", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETSTATUSES(ResponseList.class, "getStatuses"),
+    GETSTATUSES_WITH_OPTIONS(ResponseList.class, "getStatuses", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETSTATUSES_WITH_ID(ResponseList.class, "getStatuses", String.class, "userId"),
+    GETSTATUSES_WITH_ID_OPTIONS(ResponseList.class, "getStatuses", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETTAGGED(ResponseList.class, "getTagged"),
+    GETTAGGED_WITH_OPTIONS(ResponseList.class, "getTagged", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETTAGGED_WITH_ID(ResponseList.class, "getTagged", String.class, "userId"),
+    GETTAGGED_WITH_ID_OPTIONS(ResponseList.class, "getTagged", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKEPOST(Boolean.class,  "likePost", String.class, "postId"),
+    POSTFEED(String.class, "postFeed", PostUpdate.class, "postUpdate"),
+    POSTFEED_WITH_POSTUPDATE(String.class, "postFeed", String.class, "userId", PostUpdate.class, "postUpdate"),
+    POSTLINK(String.class, "postLink", URL.class, "link"),
+    POSTLINK_WITH_MSG(String.class, "postLink", URL.class, "link", String.class, "message"),
+    POSTLINK_WITH_ID(String.class, "postLink", String.class, "userId", URL.class, "link"),
+    POSTLINK_WITH_ID_MSG(String.class, "postLink", String.class, "userId", URL.class, "link", String.class, "message"),
+    POSTSTATUSMESSAGE(String.class, "postStatusMessage", String.class, "message"),
+    POSTSTATUSMESSAGE_WITH_ID(String.class, "postStatusMessage", String.class, "userId", String.class, "message"),
+    UNLIKEPOST(Boolean.class,  "unlikePost", String.class, "postId"),
+
+    // QuestionMethods
+    ADDQUESTIONOPTION(String.class, "addQuestionOption", String.class, "questionId", String.class, "optionDescription"),
+    CREATEQUESTION(String.class, "createQuestion", String.class, "question"),
+    CREATEQUESTION_WITH_OPTIONS(String.class, "createQuestion", String.class, "question", List.class, "options", boolean.class, "allowNewOptions"),
+    CREATEQUESTION_WITH_ID(String.class, "createQuestion", String.class, "userId", String.class, "question"),
+    CREATEQUESTION_WITH_ID_OPTIONS(String.class, "createQuestion", String.class, "userId", String.class, "question", List.class, "options", boolean.class, "allowNewOptions"),
+    DELETEQUESTION(Boolean.class,  "deleteQuestion", String.class, "questionId"),
+    GETQUESTION(Question.class,  "getQuestion", String.class, "questionId"),
+    GETQUESTION_WITH_OPTIONS(Question.class,  "getQuestion", String.class, "questionId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETQUESTIONOPTIONS(ResponseList.class, "getQuestionOptions", String.class, "questionId"),
+    GETQUESTIONOPTIONS_WITH_OPTIONS(ResponseList.class, "getQuestionOptions", String.class, "questionId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETQUESTIONOPTIONVOTES(ResponseList.class, "getQuestionOptionVotes", String.class, "questionId"),
+    GETQUESTIONS(ResponseList.class, "getQuestions"),
+    GETQUESTIONS_WITH_OPTIONS(ResponseList.class, "getQuestions", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETQUESTIONS_WITH_ID(ResponseList.class, "getQuestions", String.class, "userId"),
+    GETQUESTIONS_WITH_ID_OPTIONS(ResponseList.class, "getQuestions", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // SubscribeMethods
+    GETSUBSCRIBEDTO(ResponseList.class, "getSubscribedto"),
+    GETSUBSCRIBEDTO_WITH_OPTIONS(ResponseList.class, "getSubscribedto", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETSUBSCRIBEDTO_WITH_ID(ResponseList.class, "getSubscribedto", String.class, "userId"),
+    GETSUBSCRIBEDTO_WITH_ID_OPTIONS(ResponseList.class, "getSubscribedto", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETSUBSCRIBERS(ResponseList.class, "getSubscribers"),
+    GETSUBSCRIBERS_WITH_OPTIONS(ResponseList.class, "getSubscribers", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETSUBSCRIBERS_WITH_ID(ResponseList.class, "getSubscribers", String.class, "userId"),
+    GETSUBSCRIBERS_WITH_ID_OPTIONS(ResponseList.class, "getSubscribers", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+
+    // TestUserMethods
+    CREATETESTUSER(TestUser.class,  "createTestUser", String.class, "appId"),
+    CREATETESTUSER_WITH_NAME(TestUser.class,  "createTestUser", String.class, "appId", String.class, "name", String.class, "userLocale", String.class, "permissions"),
+    DELETETESTUSER(Boolean.class,  "deleteTestUser", String.class, "testUserId"),
+    GETTESTUSERS(List.class, "getTestUsers", String.class, "appId"),
+    MAKEFRIENDTESTUSER(Boolean.class,  "makeFriendTestUser", TestUser.class, "testUser1", TestUser.class, "testUser2"),
+
+    // UserMethods
+    GETME(User.class,  "getMe"),
+    GETME_WITH_OPTIONS(User.class,  "getMe", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETPICTUREURL(URL.class,  "getPictureURL"),
+    GETPICTUREURL_WITH_PICTURESIZE(URL.class,  "getPictureURL", PictureSize.class, "size"),
+    GETPICTUREURL_WITH_ID(URL.class,  "getPictureURL", String.class, "userId"),
+    GETPICTUREURL_WITH_ID_PICTURESIZE(URL.class,  "getPictureURL", String.class, "userId", PictureSize.class, "size"),
+    GETUSER(User.class,  "getUser", String.class, "userId"),
+    GETUSER_WITH_OPTIONS(User.class,  "getUser", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETUSERS(List.class, "getUsers", new String[0].getClass(), "ids"),
+
+    // VideoMethods
+    COMMENTVIDEO(String.class, "commentVideo", String.class, "videoId", String.class, "message"),
+    GETVIDEO(Video.class,  "getVideo", String.class, "videoId"),
+    GETVIDEO_WITH_OPTIONS(Video.class,  "getVideo", String.class, "videoId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETVIDEOCOMMENTS(ResponseList.class, "getVideoComments", String.class, "videoId"),
+    GETVIDEOCOMMENTS_WITH_OPTIONS(ResponseList.class, "getVideoComments", String.class, "videoId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETVIDEOCOVER(URL.class,  "getVideoCover", String.class, "videoId"),
+    GETVIDEOLIKES(ResponseList.class, "getVideoLikes", String.class, "videoId"),
+    GETVIDEOLIKES_WITH_OPTIONS(ResponseList.class, "getVideoLikes", String.class, "videoId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETVIDEOS(ResponseList.class, "getVideos"),
+    GETVIDEOS_WITH_OPTIONS(ResponseList.class, "getVideos", Reading.class, FacebookConstants.READING_PPROPERTY),
+    GETVIDEOS_WITH_ID(ResponseList.class, "getVideos", String.class, "userId"),
+    GETVIDEOS_WITH_ID_OPTIONS(ResponseList.class, "getVideos", String.class, "userId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    LIKEVIDEO(Boolean.class,  "likeVideo", String.class, "videoId"),
+    POSTVIDEO(String.class, "postVideo", Media.class, "source"),
+    POSTVIDEO_WITH_TITLE(String.class, "postVideo", Media.class, "source", String.class, "title", String.class, "description"),
+    POSTVIDEO_WITH_ID(String.class, "postVideo", String.class, "userId", Media.class, "source"),
+    POSTVIDEO_WITH_ID_MEDIA(String.class, "postVideo", String.class, "userId", Media.class, "source", String.class, "title", String.class, "description"),
+    UNLIKEVIDEO(Boolean.class,  "unlikeVideo", String.class, "videoId"),
+
+    // SearchMethods get the highest priority with higher ordinal values
+    SEARCH(ResponseList.class, "search", String.class, "query"),
+    SEARCH_WITH_OPTIONS(ResponseList.class, "search", String.class, "query", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHCHECKINS(ResponseList.class, "searchCheckins"),
+    SEARCHCHECKINS_WITH_OPTIONS(ResponseList.class, "searchCheckins", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHEVENTS(ResponseList.class, "searchEvents", String.class, "query"),
+    SEARCHEVENTS_WITH_OPTIONS(ResponseList.class, "searchEvents", String.class, "query", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHGROUPS(ResponseList.class, "searchGroups", String.class, "query"),
+    SEARCHGROUPS_WITH_OPTIONS(ResponseList.class, "searchGroups", String.class, "query", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHLOCATIONS(ResponseList.class, "searchLocations", GeoLocation.class, "center", int.class, "distance"),
+    SEARCHLOCATIONS_WITH_OPTIONS(ResponseList.class, "searchLocations", GeoLocation.class, "center", int.class, "distance", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHLOCATIONS_WITH_ID(ResponseList.class, "searchLocations", String.class, "placeId"),
+    SEARCHLOCATIONS_WITH_ID_OPTIONS(ResponseList.class, "searchLocations", String.class, "placeId", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHPLACES(ResponseList.class, "searchPlaces", String.class, "query"),
+    SEARCHPLACES_WITH_OPTIONS(ResponseList.class, "searchPlaces", String.class, "query", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHPLACES_WITH_CENTER(ResponseList.class, "searchPlaces", String.class, "query", GeoLocation.class, "center", int.class, "distance"),
+    SEARCHPLACES_WITH_CENTER_OPTIONS(ResponseList.class, "searchPlaces", String.class, "query", GeoLocation.class, "center", int.class, "distance", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHPOSTS(ResponseList.class, "searchPosts", String.class, "query"),
+    SEARCHPOSTS_WITH_OPTIONS(ResponseList.class, "searchPosts", String.class, "query", Reading.class, FacebookConstants.READING_PPROPERTY),
+    SEARCHUSERS(ResponseList.class, "searchUsers", String.class, "query"),
+    SEARCHUSERS_WITH_OPTIONS(ResponseList.class, "searchUsers", String.class, "query", Reading.class, FacebookConstants.READING_PPROPERTY);
+
+    // name, result class, ordered argument names and classes, and Method to invoke
+    private final String name;
+    private final Class resultType;
+    private final List<String> argNames;
+    private final List<Class> argTypes;
+    private final Method method;
+
+    private FacebookMethodsType(Class resultType, String name, Object... args) throws IllegalArgumentException {
+        this.name = name;
+        this.resultType = resultType;
+
+        if (args.length % 2 != 0) {
+            throw new IllegalArgumentException("Invalid parameter list, "
+                + "must be of the form 'Class arg1, String arg1Name, Class arg2, String arg2Name...");
+        }
+        int nArgs = args.length / 2;
+        this.argNames = new ArrayList<String>(nArgs);
+        this.argTypes = new ArrayList<Class>(nArgs);
+        for (int i = 0; i < nArgs; i++) {
+            this.argTypes.add((Class) args[i * 2]);
+            this.argNames.add((String) args[i * 2 + 1]);
+        }
+
+        // find method in Facebook type
+        try {
+            this.method = Facebook.class.getMethod(name, argTypes.toArray(new Class[nArgs]));
+        } catch (NoSuchMethodException e) {
+            throw new IllegalArgumentException(
+                String.format("Missing method %s %s", name, argTypes.toString().replace('[', '(').replace(']', ')')),
+                e);
+        }
+    }
+
+    /**
+     * Find method type by name and argument types.
+     * @param name method name
+     * @param args ordered argument types
+     * @return matching method, null if not found
+     */
+    public static FacebookMethodsType findMethod(String name, Class... args) {
+        for (FacebookMethodsType method : values()) {
+            if (method.name.equals(name)) {
+                if ((method.argTypes.isEmpty() && (args == null || args.length == 0))
+                    || Arrays.equals(method.argTypes.toArray(), args)) {
+                    return method;
+                }
+            }
+        }
+
+        return null;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public Class getResultType() {
+        return resultType;
+    }
+
+    public List<String> getArgNames() {
+        return Collections.unmodifiableList(argNames);
+    }
+
+    public List<Class> getArgTypes() {
+        return Collections.unmodifiableList(argTypes);
+    }
+
+    public Method getMethod() {
+        return method;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder builder = new StringBuilder();
+        builder.append("{")
+            .append("name=").append(name)
+            .append(", resultType=").append(resultType)
+            .append(", argNames=").append(argNames)
+            .append(", argTypes=").append(argTypes)
+            .append("}");
+        return builder.toString();
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java
new file mode 100644
index 0000000..1e78dac
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookMethodsTypeHelper.java
@@ -0,0 +1,366 @@
+/**
+ * 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.facebook.data;
+
+import java.lang.reflect.Array;
+import java.util.*;
+import org.apache.camel.RuntimeCamelException;
+import org.apache.camel.component.facebook.FacebookConstants;
+import org.apache.camel.component.facebook.config.FacebookNameStyle;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import facebook4j.Facebook;
+import facebook4j.FacebookException;
+
+
+/**
+ * Helper class for working with {@link FacebookMethodsType}.
+ */
+public final class FacebookMethodsTypeHelper {
+
+    private static final Logger LOG = LoggerFactory.getLogger(FacebookMethodsTypeHelper.class);
+
+    // maps method name to FacebookMethodsType
+    private static final Map<String, List<FacebookMethodsType>> METHOD_MAP =
+        new HashMap<String, List<FacebookMethodsType>>();
+
+    // maps method name to method arguments of the form Class type1, String name1, Class type2, String name2,...
+    private static final Map<String, List<Object>> ARGUMENTS_MAP =
+        new HashMap<String, List<Object>>();
+
+    // maps argument name to argument type
+    private static final Map<String, Class> VALID_ARGUMENTS =
+        new HashMap<String, Class>();
+
+    static {
+        final FacebookMethodsType[] methods = FacebookMethodsType.values();
+        // load lookup maps for FacebookMethodsType
+        for (FacebookMethodsType method : methods) {
+
+            // map method name to Enum
+            final String name = method.getName();
+            List<FacebookMethodsType> overloads = METHOD_MAP.get(name);
+            if (overloads == null) {
+                overloads = new ArrayList<FacebookMethodsType>();
+                METHOD_MAP.put(method.getName(), overloads);
+            }
+            overloads.add(method);
+
+            // add arguments for this method
+            List<Object> arguments = ARGUMENTS_MAP.get(name);
+            if (arguments == null) {
+                arguments = new ArrayList<Object>();
+                ARGUMENTS_MAP.put(name, arguments);
+            }
+
+            // process all arguments for this method
+            final int nArgs = method.getArgNames().size();
+            final String[] argNames = method.getArgNames().toArray(new String[nArgs]);
+            final Class[] argTypes = method.getArgTypes().toArray(new Class[nArgs]);
+            for (int i = 0; i < nArgs; i++) {
+                final String argName = argNames[i];
+                final Class argType = argTypes[i];
+                if (!arguments.contains(argName)) {
+                    arguments.add(argType);
+                    arguments.add(argName);
+                }
+
+                // also collect argument names for all methods, also detect clashes here
+                final Class previousType = VALID_ARGUMENTS.get(argName);
+                if (previousType != null && previousType != argType) {
+                    throw new ExceptionInInitializerError(String.format(
+                        "Argument %s has ambiguous types (%s, %s) across methods!",
+                        name, previousType, argType));
+                } else if (previousType == null) {
+                    VALID_ARGUMENTS.put(argName, argType);
+                }
+            }
+
+        }
+
+        // add endpoint parameter inBody for producers
+        VALID_ARGUMENTS.put(FacebookConstants.IN_BODY_PROPERTY, String.class);
+
+        LOG.debug("Found {} unique method names in {} methods", METHOD_MAP.size(), methods.length);
+
+    }
+
+    private FacebookMethodsTypeHelper() {
+    }
+
+    /**
+     * Gets methods that match the given name and arguments.<p/>
+     * Note that the args list is a required subset of arguments for returned methods.
+     * @param name case sensitive full method name to lookup
+     * @param argNames unordered required argument names
+     * @return non-null unmodifiable list of methods that take all of the given arguments, empty if there is no match
+     */
+    public static List<FacebookMethodsType> getCandidateMethods(String name, String... argNames) {
+        final List<FacebookMethodsType> methods = METHOD_MAP.get(name);
+        if (methods == null) {
+            LOG.debug("No matching method for method {}", name);
+            return Collections.emptyList();
+        }
+        int nArgs = argNames != null ? argNames.length : 0;
+        if (nArgs == 0) {
+            LOG.debug("Found {} methods for method {}", methods.size(), name);
+            return Collections.unmodifiableList(methods);
+        } else {
+            final List<FacebookMethodsType> filteredSet = filterMethods(methods, MatchType.SUBSET, argNames);
+            if (LOG.isDebugEnabled()) {
+                LOG.debug("Found {} filtered methods for {}",
+                    filteredSet.size(), name + Arrays.toString(argNames).replace('[', '(').replace(']', ')'));
+            }
+            return filteredSet;
+        }
+    }
+
+    /**
+     * Filters a list of methods to those that take the given set of arguments.
+     *
+     * @param methods list of methods to filter
+     * @param matchType whether the arguments are an exact match, a subset or a super set of method args
+     * @param argNames argument names to filter the list
+     * @return methods with arguments that satisfy the match type.<p/>
+     * For SUPER_SET match, if methods with exact match are found, methods that take a subset are ignored
+     */
+    public static List<FacebookMethodsType> filterMethods(List<FacebookMethodsType> methods, MatchType matchType,
+                                                          String... argNames) {
+        List<String> argsList = Arrays.asList(argNames);
+        // list of methods that have all args in the given names
+        final List<FacebookMethodsType> result = new ArrayList<FacebookMethodsType>();
+        final List<FacebookMethodsType> extraArgs = new ArrayList<FacebookMethodsType>();
+
+        for (FacebookMethodsType method : methods) {
+            final List<String> methodArgs = method.getArgNames();
+            switch (matchType) {
+            case EXACT:
+                // method must take all args, and no more
+                if (methodArgs.containsAll(argsList) && argsList.containsAll(methodArgs)) {
+                    result.add(method);
+                }
+                break;
+            case SUBSET:
+                // all args are required, method may take more
+                if (methodArgs.containsAll(argsList)) {
+                    result.add(method);
+                }
+                break;
+            default:
+            case SUPER_SET:
+                // all method args must be present
+                if (argsList.containsAll(methodArgs)) {
+                    if (methodArgs.containsAll(argsList)) {
+                        // prefer exact match to avoid unused args
+                        result.add(method);
+                    } else {
+                        // method takes a subset, unused args
+                        extraArgs.add(method);
+                    }
+                }
+                break;
+            }
+        }
+
+        return Collections.unmodifiableList(result.isEmpty() ? extraArgs : result);
+    }
+
+    /**
+     * Gets argument types and names for all overloaded methods with the given name.
+     * @param name method name, must be a long form (i.e. get*, or search*)
+     * @return list of arguments of the form Class type1, String name1, Class type2, String name2,...
+     */
+    public static List<Object> getArguments(String name) throws IllegalArgumentException {
+        final List<Object> arguments = ARGUMENTS_MAP.get(name);
+        if (arguments == null) {
+            throw new IllegalArgumentException(name);
+        }
+        return Collections.unmodifiableList(arguments);
+    }
+
+    /**
+     * Gets argument types and names for all overloaded methods with the given short form name.
+     * @param name method name, may be a short form
+     * @param style name style
+     * @return list of arguments of the form Class type1, String name1, Class type2, String name2,...
+     */
+    public static List<Object> getArgumentsForNameStyle(String name, FacebookNameStyle style) throws IllegalArgumentException {
+        if (style == null) {
+            throw new IllegalArgumentException("Parameters style cannot be null");
+        }
+        switch (style) {
+        case EXACT:
+            return getArguments(name);
+        case GET:
+            return getArguments(convertToGetMethod(name));
+        case SEARCH:
+            return getArguments(convertToSearchMethod(name));
+        case GET_AND_SEARCH:
+        default:
+            final List<Object> arguments = new ArrayList<Object>();
+            arguments.addAll(getArguments(convertToGetMethod(name)));
+            arguments.addAll(getArguments(convertToSearchMethod(name)));
+            return Collections.unmodifiableList(arguments);
+        }
+    }
+
+    /**
+     * Get missing properties.
+     * @param methodName method name
+     * @param nameStyle method name style
+     * @param argNames available arguments
+     * @return Set of missing argument names
+     */
+    public static Set<String> getMissingProperties(String methodName, FacebookNameStyle nameStyle, Set<String> argNames) {
+        final List<Object> argsWithTypes = getArgumentsForNameStyle(methodName, nameStyle);
+        final Set<String> missingArgs = new HashSet<String>();
+
+        for (int i = 1; i < argsWithTypes.size(); i += 2) {
+            final String name = (String) argsWithTypes.get(i);
+            if (!argNames.contains(name)) {
+                missingArgs.add(name);
+            }
+        }
+
+        return missingArgs;
+    }
+
+    /**
+     * Get argument types and names used by all methods.
+     * @return map with argument names as keys, and types as values
+     */
+    public static Map<String, Class> allArguments() {
+        return Collections.unmodifiableMap(VALID_ARGUMENTS);
+    }
+
+    /**
+     * Get the type for the given argument name.
+     * @param argName argument name
+     * @return argument type
+     */
+    public static Class getType(String argName) throws IllegalArgumentException {
+        final Class type = VALID_ARGUMENTS.get(argName);
+        if (type == null) {
+            throw new IllegalArgumentException(argName);
+        }
+        return type;
+    }
+
+    public static String convertToGetMethod(String name) throws IllegalArgumentException {
+        if (name == null || name.isEmpty()) {
+            throw new IllegalArgumentException("Name cannot be null or empty");
+        }
+        return "get" + Character.toUpperCase(name.charAt(0)) + name.substring(1);
+    }
+
+    public static String convertToSearchMethod(String name) throws IllegalArgumentException {
+        if (name == null || name.isEmpty()) {
+            throw new IllegalArgumentException("Name cannot be null or empty");
+        }
+        return "search" + Character.toUpperCase(name.charAt(0)) + name.substring(1);
+    }
+
+    public static FacebookMethodsType getHighestPriorityMethod(List<FacebookMethodsType> filteredMethods) {
+        FacebookMethodsType highest = null;
+        for (FacebookMethodsType method : filteredMethods) {
+            if (highest == null || method.ordinal() > highest.ordinal()) {
+                highest = method;
+            }
+        }
+        return highest;
+    }
+
+    /**
+     * Invokes given method with argument values from given properties.
+     *
+     * @param facebook Facebook4J target object for invoke
+     * @param method method to invoke
+     * @param properties Map of arguments
+     * @return result of method invocation
+     * @throws RuntimeCamelException on errors
+     */
+    @SuppressWarnings("unchecked")
+    public static Object invokeMethod(Facebook facebook, FacebookMethodsType method, Map<String, Object> properties)
+        throws RuntimeCamelException {
+
+        LOG.debug("Invoking {} with arguments {}", method.getName(), properties);
+
+        final List<String> argNames = method.getArgNames();
+        final Object[] values = new Object[argNames.size()];
+        final List<Class> argTypes = method.getArgTypes();
+        final Class[] types = argTypes.toArray(new Class[argTypes.size()]);
+        int index = 0;
+        for (String name : argNames) {
+            Object value = properties.get(name);
+
+            // is the parameter an array type?
+            if (value != null && types[index].isArray()) {
+                Class type = types[index];
+
+                if (value instanceof Collection) {
+                    // convert collection to array
+                    Collection collection = (Collection) value;
+                    Object array = Array.newInstance(type.getComponentType(), collection.size());
+                    if (array instanceof Object[]) {
+                        collection.toArray((Object[]) array);
+                    } else {
+                        int i = 0;
+                        for (Object el : collection) {
+                            Array.set(array, i++, el);
+                        }
+                    }
+                    value = array;
+                } else if (value.getClass().isArray()
+                    && type.getComponentType().isAssignableFrom(value.getClass().getComponentType())) {
+                    // convert derived array to super array
+                    final int size = Array.getLength(value);
+                    Object array = Array.newInstance(type.getComponentType(), size);
+                    for (int i = 0; i < size; i++) {
+                        Array.set(array, i, Array.get(value, i));
+                    }
+                    value = array;
+                } else {
+                    throw new IllegalArgumentException(
+                        String.format("Cannot convert %s to %s", value.getClass(), type));
+                }
+            }
+
+            values[index++] = value;
+        }
+
+        try {
+            return method.getMethod().invoke(facebook, values);
+        } catch (Throwable e) {
+            // skip wrapper exception to simplify stack
+            String msg;
+            if (e.getCause() != null && e.getCause() instanceof FacebookException) {
+                e = e.getCause();
+                msg = ((FacebookException)e).getErrorMessage();
+            } else {
+                msg = e.getMessage();
+            }
+            throw new RuntimeCamelException(
+                String.format("Error invoking %s with %s: %s", method.getName(), properties, msg), e);
+        }
+    }
+
+    public static enum MatchType {
+        EXACT, SUBSET, SUPER_SET
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java
new file mode 100644
index 0000000..5a61d2c
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/FacebookPropertiesHelper.java
@@ -0,0 +1,132 @@
+/**
+ * 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.facebook.data;
+
+import java.lang.reflect.Field;
+import java.util.*;
+import org.apache.camel.Exchange;
+import org.apache.camel.component.facebook.FacebookConstants;
+import org.apache.camel.component.facebook.config.FacebookConfiguration;
+import org.apache.camel.component.facebook.config.FacebookEndpointConfiguration;
+import org.apache.camel.util.IntrospectionSupport;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import facebook4j.Reading;
+
+/**
+ * Helper class to work with Facebook component properties.
+ */
+public final class FacebookPropertiesHelper {
+
+    // set of field names which are specific to Facebook4J api, to be excluded from method argument considerations
+    private static final Set<String> COMPONENT_CONFIG_FIELDS = new HashSet<String>();
+
+    private static final Logger LOG = LoggerFactory.getLogger(FacebookPropertiesHelper.class);
+
+    private static final Set<String> ENDPOINT_CONFIG_FIELDS = new HashSet<String>();
+
+    static {
+        for (Field field : FacebookConfiguration.class.getDeclaredFields()) {
+            COMPONENT_CONFIG_FIELDS.add(field.getName());
+        }
+        for (Field field : FacebookEndpointConfiguration.class.getDeclaredFields()) {
+            ENDPOINT_CONFIG_FIELDS.add(field.getName());
+        }
+    }
+
+    private FacebookPropertiesHelper() {
+        // utility
+    }
+
+    /**
+     * Apply properties for {@link Reading} type to the supplied {@link FacebookEndpointConfiguration}.
+     * @param configuration endpoint configuration to update
+     * @param options properties to apply to the reading field in configuration
+     */
+    public static void configureReadingProperties(FacebookEndpointConfiguration configuration,
+                                                  Map<String, Object> options) {
+        final Map<String, Object> readingProperties = IntrospectionSupport.extractProperties(
+            options, FacebookConstants.READING_PREFIX);
+        if (!readingProperties.isEmpty()) {
+            try {
+
+                // add to an existing reading reference?
+                // NOTE Reading class does not support overwriting properties!!!
+                Reading reading = configuration.getReading();
+                if (reading == null) {
+                    reading = new Reading();
+                } else {
+                    reading = ReadingBuilder.copy(reading, false);
+                }
+                // set properties
+                ReadingBuilder.setProperties(reading,
+                    readingProperties);
+
+                // update reading in configuration
+                configuration.setReading(reading);
+
+            } catch (Exception e) {
+                throw new IllegalArgumentException(readingProperties.toString(), e);
+            }
+
+            // add any unknown properties back to options to throw an error later
+            for (Map.Entry<String, Object> entry : readingProperties.entrySet()) {
+                options.put(FacebookConstants.READING_PREFIX + entry.getKey(), entry.getValue());
+            }
+        }
+    }
+
+    /**
+     * Gets exchange header properties that start with {@link FacebookConstants}.FACEBOOK_PROPERTY_PREFIX.
+     *
+     * @param exchange Camel exchange
+     * @param properties map to collect properties with required prefix
+     */
+    public static Map<String, Object> getExchangeProperties(Exchange exchange, Map<String, Object> properties) {
+        int nProperties = 0;
+        for (Map.Entry<String, Object> entry : exchange.getIn().getHeaders().entrySet()) {
+            if (entry.getKey().startsWith(FacebookConstants.FACEBOOK_PROPERTY_PREFIX)) {
+                properties.put(entry.getKey().substring(FacebookConstants.FACEBOOK_PROPERTY_PREFIX.length()),
+                    entry.getValue());
+                nProperties++;
+            }
+        }
+        LOG.debug("Found {} properties in exchange", nProperties);
+        return properties;
+    }
+
+    public static void getEndpointProperties(FacebookEndpointConfiguration configuration,
+                                             Map<String, Object> properties) {
+        if (IntrospectionSupport.getProperties(configuration, properties, null, false)) {
+            final Set<String> names = properties.keySet();
+            // remove component config properties so we only have endpoint properties
+            names.removeAll(COMPONENT_CONFIG_FIELDS);
+        }
+        if (LOG.isDebugEnabled()) {
+            final Set<String> names = properties.keySet();
+            LOG.debug("Found endpoint properties {}", names.retainAll(ENDPOINT_CONFIG_FIELDS));
+        }
+    }
+
+    public static Set<String> getEndpointPropertyNames(FacebookEndpointConfiguration configuration) {
+        Map<String, Object> properties = new HashMap<String, Object>();
+        getEndpointProperties(configuration, properties);
+        return Collections.unmodifiableSet(properties.keySet());
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java
new file mode 100644
index 0000000..1e44887
--- /dev/null
+++ b/components/camel-facebook/src/main/java/org/apache/camel/component/facebook/data/ReadingBuilder.java
@@ -0,0 +1,121 @@
+/**
+ * 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.facebook.data;
+
+import java.lang.reflect.Field;
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.LinkedHashMap;
+import java.util.Locale;
+import java.util.Map;
+import org.apache.camel.component.facebook.FacebookConstants;
+
+import facebook4j.Reading;
+
+/**
+ * Builds {@link facebook4j.Reading} instances.
+ */
+public class ReadingBuilder {
+
+
+    public static Reading copy(Reading reading, boolean skipSinceUtil) throws NoSuchFieldException, IllegalAccessException {
+        // use private field access to make a copy
+        Field field = Reading.class.getDeclaredField("parameterMap");
+        field.setAccessible(true);
+        final LinkedHashMap<String, String> source = (LinkedHashMap<String, String>) field.get(reading);
+        // create another reading, and add all fields from source
+        Reading copy = new Reading();
+        final LinkedHashMap copyMap = new LinkedHashMap();
+        copyMap.putAll(source);
+        if (skipSinceUtil) {
+            copyMap.remove("since");
+            copyMap.remove("until");
+        }
+        field.set(copy, copyMap);
+        field.setAccessible(false);
+        return copy;
+    }
+
+    /**
+     * Sets Reading properties.
+     * @param reading Reading object to populate
+     * @param readingProperties Map to extract properties
+     */
+    public static void setProperties(Reading reading, Map<String, Object> readingProperties) {
+
+        final String fields = (String) readingProperties.remove("fields");
+        if (fields != null) {
+            reading.fields(fields.toString().split(","));
+        }
+        final Object limit = readingProperties.remove("limit");
+        if (limit != null) {
+            reading.limit(Integer.parseInt(limit.toString()));
+        }
+        final Object offset = readingProperties.remove("offset");
+        if (offset != null) {
+            reading.offset(Integer.parseInt(offset.toString()));
+        }
+        final SimpleDateFormat dateFormat = new SimpleDateFormat(FacebookConstants.FACEBOOK_DATE_FORMAT);
+        final Object until = readingProperties.remove("until");
+        if (until != null) {
+            try {
+                reading.until(dateFormat.parse(until.toString()));
+            } catch (ParseException e) {
+                throw new RuntimeException("Error parsing property 'until' :" + e.getMessage(), e);
+            }
+        }
+        final Object since = readingProperties.remove("since");
+        if (since != null) {
+            try {
+                reading.since(dateFormat.parse(since.toString()));
+            } catch (ParseException e) {
+                throw new RuntimeException("Error parsing property 'since' :" + e.getMessage(), e);
+            }
+        }
+        final Object metadata = readingProperties.remove("metadata");
+        if (metadata != null && Boolean.parseBoolean(metadata.toString())) {
+            reading.metadata();
+        }
+        final Object locale = readingProperties.remove("locale");
+        if (locale != null) {
+            String[] args = locale.toString().split(",");
+            switch (args.length) {
+            case  1:
+                reading.locale(new Locale(args[0]));
+                break;
+            case  2:
+                reading.locale(new Locale(args[0], args[1]));
+                break;
+            case  3:
+                reading.locale(new Locale(args[0], args[1], args[2]));
+                break;
+            default:
+                throw new IllegalArgumentException(String.format("Invalid value for property 'locale' %s, "
+                    + "must be of the form [language][,country][,variant]", locale.toString()));
+            }
+        }
+        final Object with = readingProperties.remove("with");
+        if (with != null && Boolean.parseBoolean(with.toString())) {
+            reading.withLocation();
+        }
+        final Object filter = readingProperties.remove("filter");
+        if (filter != null) {
+            reading.filter(filter.toString());
+        }
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/main/resources/META-INF/services/org/apache/camel/component/facebook
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/main/resources/META-INF/services/org/apache/camel/component/facebook b/components/camel-facebook/src/main/resources/META-INF/services/org/apache/camel/component/facebook
new file mode 100644
index 0000000..bad2fa3
--- /dev/null
+++ b/components/camel-facebook/src/main/resources/META-INF/services/org/apache/camel/component/facebook
@@ -0,0 +1 @@
+class=org.apache.camel.component.facebook.FacebookComponent

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java
new file mode 100644
index 0000000..1dc0f17
--- /dev/null
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/CamelFacebookTestSupport.java
@@ -0,0 +1,81 @@
+/**
+ * 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.facebook;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URL;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Properties;
+import org.apache.camel.component.facebook.config.FacebookConfiguration;
+import org.apache.camel.test.junit4.CamelTestSupport;
+import org.apache.camel.util.IntrospectionSupport;
+
+public class CamelFacebookTestSupport extends CamelTestSupport {
+
+    private final Properties properties;
+    private FacebookConfiguration configuration;
+
+    public CamelFacebookTestSupport() throws Exception {
+        URL url = getClass().getResource("/test-options.properties");
+
+        InputStream inStream;
+        try {
+            inStream = url.openStream();
+        } catch (IOException e) {
+            e.printStackTrace();
+            throw new IllegalAccessError("test-options.properties could not be found");
+        }
+
+        properties = new Properties();
+        try {
+            properties.load(inStream);
+        } catch (IOException e) {
+            e.printStackTrace();
+            throw new IllegalAccessError("test-options.properties could not be found");
+        }
+
+        Map<String, Object> options = new HashMap<String, Object>();
+        for (Map.Entry<Object, Object> entry : properties.entrySet()) {
+            options.put(entry.getKey().toString(), entry.getValue());
+        }
+
+        configuration = new FacebookConfiguration();
+        IntrospectionSupport.setProperties(configuration, options);
+    }
+
+    public FacebookConfiguration getConfiguration() {
+        return configuration;
+    }
+
+    public String getOauthParams() {
+        return "oAuthAppId=" + properties.get("oAuthAppId") + "&oAuthAppSecret=" + properties.get("oAuthAppSecret") +
+            (properties.get("oAuthAccessToken") != null ?
+                ("&oAuthAccessToken=" + properties.get("oAuthAccessToken")) : "");
+    }
+
+    protected String getShortName(String name) {
+        if (name.startsWith("get")) {
+            name = Character.toLowerCase(name.charAt(3)) + name.substring(4);
+        } else if (name.startsWith("search") && !"search".equals(name)) {
+            name = Character.toLowerCase(name.charAt(6)) + name.substring(7);
+        }
+        return name;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java
new file mode 100644
index 0000000..80476fc
--- /dev/null
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentConsumerTest.java
@@ -0,0 +1,90 @@
+/**
+ * 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.facebook;
+
+import java.lang.reflect.Method;
+import java.text.SimpleDateFormat;
+import java.util.*;
+import java.util.concurrent.TimeUnit;
+import org.apache.camel.builder.RouteBuilder;
+import org.apache.camel.component.mock.MockEndpoint;
+import org.junit.Test;
+
+import facebook4j.api.SearchMethods;
+
+public class FacebookComponentConsumerTest extends CamelFacebookTestSupport {
+
+    private final Set<String> searchNames = new HashSet<String>();
+    private List<String> excludedNames;
+
+    public FacebookComponentConsumerTest() throws Exception {
+        // find search methods for consumer tests
+        for (Method method : SearchMethods.class.getDeclaredMethods()) {
+            String name = getShortName(method.getName());
+            if (!"locations".equals(name) && !"checkins".equals(name)) {
+                searchNames.add(name);
+            }
+        }
+
+        excludedNames = Arrays.asList("places", "users", "search");
+    }
+
+    @Test
+    public void testConsumers() throws InterruptedException {
+        for (String name : searchNames) {
+            MockEndpoint mock;
+            if (!excludedNames.contains(name)) {
+                mock = getMockEndpoint("mock:consumeResult" + name);
+                mock.expectedMinimumMessageCount(1);
+            }
+
+            mock = getMockEndpoint("mock:consumeQueryResult" + name);
+            mock.expectedMinimumMessageCount(1);
+        }
+
+        assertMockEndpointsSatisfied();
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            public void configure() {
+
+                // start with a 7 day window for the first delayed poll
+                String since = new SimpleDateFormat(FacebookConstants.FACEBOOK_DATE_FORMAT).format(
+                    new Date(System.currentTimeMillis() - TimeUnit.MILLISECONDS.convert(7, TimeUnit.DAYS)));
+
+                for (String name : searchNames) {
+                    if (!excludedNames.contains(name)) {
+                        // consumer.sendEmptyMessageWhenIdle is true since user may not have some items like events
+                        from("facebook://" + name + "?reading.limit=10&reading.locale=en.US&reading.since="
+                            + since + "&consumer.initialDelay=1000&consumer.sendEmptyMessageWhenIdle=true&"
+                            + getOauthParams())
+                            .to("mock:consumeResult" + name);
+                    }
+
+                    from("facebook://" + name + "?query=cheese&reading.limit=10&reading.locale=en.US&reading.since="
+                        + since + "&consumer.initialDelay=1000&" + getOauthParams())
+                        .to("mock:consumeQueryResult" + name);
+                }
+
+                // TODO add tests for the rest of the supported methods
+            }
+        };
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/1c293408/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java
----------------------------------------------------------------------
diff --git a/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java
new file mode 100644
index 0000000..bc8b65b
--- /dev/null
+++ b/components/camel-facebook/src/test/java/org/apache/camel/component/facebook/FacebookComponentProducerTest.java
@@ -0,0 +1,127 @@
+/**
+ * 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.facebook;
+
+import java.lang.reflect.Method;
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import org.apache.camel.builder.RouteBuilder;
+import org.apache.camel.component.mock.MockEndpoint;
+import org.junit.Test;
+
+import facebook4j.Facebook;
+
+public class FacebookComponentProducerTest extends CamelFacebookTestSupport {
+
+    private final Set<String> noArgNames = new HashSet<String>();
+
+    private final List<String> idExcludes;
+    private final List<String> readingExcludes;
+
+    public FacebookComponentProducerTest() throws Exception {
+        for (Class clazz : Facebook.class.getInterfaces()) {
+            final String clazzName = clazz.getSimpleName();
+            if (clazzName.endsWith("Methods") && !clazzName.equals("GameMethods")) {
+                for (Method method : clazz.getDeclaredMethods()) {
+                    // find all the no-arg methods
+                    if (method.getParameterTypes().length == 0) {
+                        noArgNames.add(getShortName(method.getName()));
+                    }
+                }
+            }
+        }
+
+        idExcludes = Arrays.asList("me", "home", "searchCheckins");
+        readingExcludes = Arrays.asList("pictureURL", "permissions");
+    }
+
+    @Test
+    public void testProducers() throws Exception {
+        for (String name : noArgNames) {
+            MockEndpoint mock = getMockEndpoint("mock:result" + name);
+            mock.expectedMinimumMessageCount(1);
+            template().sendBody("direct://test" + name, null);
+
+            // with user id
+            if (!idExcludes.contains(name)) {
+                mock = getMockEndpoint("mock:resultId" + name);
+                mock.expectedMinimumMessageCount(1);
+                template().sendBody("direct://testId" + name, null);
+            }
+
+            // with reading
+            if (!readingExcludes.contains(name)) {
+                mock = getMockEndpoint("mock:resultReading" + name);
+                mock.expectedMinimumMessageCount(1);
+                template().sendBody("direct://testReading" + name, null);
+            }
+
+            // with user id and reading
+            if (!(idExcludes.contains(name) || readingExcludes.contains(name))) {
+                mock = getMockEndpoint("mock:resultIdReading" + name);
+                mock.expectedMinimumMessageCount(1);
+                template().sendBody("direct://testIdReading" + name, null);
+            }
+        }
+
+        assertMockEndpointsSatisfied();
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            public void configure() {
+
+                //---------------
+                // producer tests
+                //---------------
+                // generate test routes for all methods with no args
+                for (String name : noArgNames) {
+                    from("direct://test" + name)
+                      .to("facebook://" + name + "?" + getOauthParams())
+                      .to("mock:result" + name);
+
+                    // with user id
+                    if (!idExcludes.contains(name)) {
+                        from("direct://testId" + name)
+                          .to("facebook://" + name + "?userId=me&" + getOauthParams())
+                          .to("mock:resultId" + name);
+                    }
+
+                    // reading options
+                    if (!readingExcludes.contains(name)) {
+                        from("direct://testReading" + name)
+                          .to("facebook://" + name + "?reading.limit=10&reading.locale=en,US&" + getOauthParams())
+                          .to("mock:resultReading" + name);
+                    }
+
+                    // with id and reading options
+                    if (!(idExcludes.contains(name) || readingExcludes.contains(name))) {
+                        from("direct://testIdReading" + name)
+                          .to("facebook://" + name + "?userId=me&reading.limit=10&reading.locale=en,US&" + getOauthParams())
+                          .to("mock:resultIdReading" + name);
+                    }
+                }
+
+                // TODO add tests for the rest of the supported methods
+            }
+        };
+    }
+
+}