Index: src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/TestBean.java
===================================================================
--- src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/TestBean.java	(revision 640)
+++ src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/TestBean.java	(working copy)
@@ -26,7 +26,17 @@
 //   private PublicFieldsDTO dto = new PublicFieldsDTO("abc");
    private AnotherBean nestedBean;
    private BeanWithCollections collections;
+   
+   private AbtractRootBean rootBean;
 
+   public AbtractRootBean getRootBean() {
+      return this.rootBean;
+   }
+
+   public void setRootBean(AbtractRootBean rootBean) {
+      this.rootBean = rootBean;
+   }
+
    public Object getObject()
    {
       return object;
Index: src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/SonBean1.java
===================================================================
--- src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/SonBean1.java	(revision 0)
+++ src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/SonBean1.java	(revision 0)
@@ -0,0 +1,50 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean.test;
+
+/**
+ * The first child.
+ */
+public class SonBean1 extends AbtractRootBean {
+
+    private String string1;
+
+    /**
+     * getter for the string1 property.
+     *
+     * @return the string1
+     */
+    public String getString1() {
+        return this.string1;
+    }
+
+    /**
+     * setter for the string1 property.
+     *
+     * @param string1 the string1 to set
+     */
+    public void setString1(String string1) {
+        this.string1 = string1;
+    }
+    
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public String toString() {
+        return string1;
+    }
+}
Index: src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/SonBean2.java
===================================================================
--- src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/SonBean2.java	(revision 0)
+++ src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/SonBean2.java	(revision 0)
@@ -0,0 +1,50 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean.test;
+
+/**
+ * The second child.
+ */
+public class SonBean2 extends AbtractRootBean {
+
+    private String string2;
+
+    /**
+     * getter for the string2 property.
+     *
+     * @return the string2
+     */
+    public String getString2() {
+        return this.string2;
+    }
+
+    /**
+     * setter for the string2 property.
+     *
+     * @param string2 the string2 to set
+     */
+    public void setString2(String string2) {
+        this.string2 = string2;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public String toString() {
+        return string2;
+    }
+}
Index: src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/AbtractRootBean.java
===================================================================
--- src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/AbtractRootBean.java	(revision 0)
+++ src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/AbtractRootBean.java	(revision 0)
@@ -0,0 +1,23 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean.test;
+
+/**
+ * An abstract class.
+ */
+public abstract class AbtractRootBean {
+
+}
Index: src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/BeanDeclaration.java
===================================================================
--- src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/BeanDeclaration.java	(revision 0)
+++ src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/test/BeanDeclaration.java	(revision 0)
@@ -0,0 +1,26 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean.test;
+
+import com.pietschy.gwt.pectin.client.bean.Beans;
+
+/**
+ * interfaces used only to trigger metadata generation for beans.
+ */
+@Beans( { AnotherBean.class, BeanWithCollections.class, TestBean.class, AbtractRootBean.class, SonBean1.class, SonBean2.class })
+public interface BeanDeclaration {
+
+}
Index: src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/BeanModelProviderFactoryTest.java
===================================================================
--- src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/BeanModelProviderFactoryTest.java	(revision 0)
+++ src/gwtTest/java/com/pietschy/gwt/pectin/client/bean/BeanModelProviderFactoryTest.java	(revision 0)
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean;
+
+import com.google.gwt.junit.client.GWTTestCase;
+import com.pietschy.gwt.pectin.client.bean.test.AnotherBean;
+import com.pietschy.gwt.pectin.client.bean.test.TestBean;
+import com.pietschy.gwt.pectin.client.value.MutableValueModel;
+
+public class BeanModelProviderFactoryTest extends GWTTestCase {
+    
+    public String getModuleName()
+    {
+       return "com.pietschy.gwt.pectin.PectinTest";
+    }
+    
+
+    public  <T> Object readProperty(BeanModelProvider<T> provider, T bean, String path) {
+        PropertyDescriptor propertyDescriptor = provider.getPropertyDescriptor(path);
+        if(propertyDescriptor.getParentPath() == null) {
+            return propertyDescriptor.readProperty(bean);
+        } else {
+            Object subBean = readProperty(provider, bean, propertyDescriptor.getParentPath());
+            return propertyDescriptor.readProperty(subBean);
+        }
+    }
+    
+    public  <T> void writeProperty(BeanModelProvider<T> provider, T bean, String path, Object value) {
+        PropertyDescriptor propertyDescriptor = provider.getPropertyDescriptor(path);
+        if(propertyDescriptor.getParentPath() == null) {
+            propertyDescriptor.writeProperty(bean, value);
+        } else {
+            Object subBean = readProperty(provider, bean, propertyDescriptor.getParentPath());
+            propertyDescriptor.writeProperty(subBean, value);
+        }
+    }
+
+    public void testNestedProperties() {
+        BeanModelProvider<TestBean> provider = BeanModelProviderFactory.get().getBeanModelProvider(TestBean.class);
+        MutableValueModel<String> stringValueModel = provider.getValueModel("nestedBean.string", String.class); 
+        MutableValueModel<AnotherBean> anotherBeanValueModel = provider.getValueModel("nestedBean", AnotherBean.class); 
+        
+        TestBean tb = new TestBean();
+        AnotherBean ab = new AnotherBean();
+        ab.setString("value");
+        tb.setNestedBean(ab);
+        
+        assertEquals(ab, readProperty(provider, tb, "nestedBean"));
+        assertEquals("value",  readProperty(provider, tb, "nestedBean.string"));
+        writeProperty(provider, tb, "nestedBean.string", "hello" );
+        assertEquals("hello", ab.getString());
+        ab.setString("value");
+        
+        provider.setValue(tb);
+        
+        assertEquals(ab, anotherBeanValueModel.getValue());
+        assertEquals("value", stringValueModel.getValue());
+        stringValueModel.setValue("hello");
+        provider.commit();
+        assertEquals("hello", ab.getString());
+    }
+
+}
Index: src/gwtTest/java/com/pietschy/gwt/pectin/client/PectinTestSuite.java
===================================================================
--- src/gwtTest/java/com/pietschy/gwt/pectin/client/PectinTestSuite.java	(revision 640)
+++ src/gwtTest/java/com/pietschy/gwt/pectin/client/PectinTestSuite.java	(working copy)
@@ -16,7 +16,11 @@
 
 package com.pietschy.gwt.pectin.client;
 
+import junit.framework.Test;
+import junit.framework.TestSuite;
+
 import com.google.gwt.junit.tools.GWTTestSuite;
+import com.pietschy.gwt.pectin.client.bean.BeanModelProviderFactoryTest;
 import com.pietschy.gwt.pectin.client.bean.BeanModelProviderGeneralTest;
 import com.pietschy.gwt.pectin.client.bean.BeanModelProviderListModelTest;
 import com.pietschy.gwt.pectin.client.bean.BeanModelProviderPropertyDescriptorTest;
@@ -25,8 +29,6 @@
 import com.pietschy.gwt.pectin.client.binding.FormBinderUiCommandTest;
 import com.pietschy.gwt.pectin.client.metadata.binding.MetadataBinderTest;
 import com.pietschy.gwt.pectin.client.style.StyleBinderTest;
-import junit.framework.Test;
-import junit.framework.TestSuite;
 
 
 /**
@@ -50,6 +52,7 @@
       gwtTestSuite.addTestSuite(BeanModelProviderValueModelTest.class);
       gwtTestSuite.addTestSuite(BeanModelProviderListModelTest.class);
       gwtTestSuite.addTestSuite(BeanModelProviderGeneralTest.class);
+      gwtTestSuite.addTestSuite(BeanModelProviderFactoryTest.class);
 
       // Binder tests
       gwtTestSuite.addTestSuite(FormBinderUiCommandTest.class);
Index: src/main/java/com/pietschy/gwt/pectin/Pectin.gwt.xml
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/Pectin.gwt.xml	(revision 640)
+++ src/main/java/com/pietschy/gwt/pectin/Pectin.gwt.xml	(working copy)
@@ -20,6 +20,10 @@
       <when-type-assignable class="com.pietschy.gwt.pectin.client.bean.BeanModelProvider"/>
    </generate-with>
 
+    <generate-with class="com.pietschy.gwt.pectin.rebind.BeanModelProviderFactoryGenerator">
+      <when-type-assignable class="com.pietschy.gwt.pectin.client.bean.BeanModelProviderFactory" />
+    </generate-with>
+
    <stylesheet src="pectin/Validation.css"/>
    <stylesheet src="pectin/Metadata.css"/>
 
Index: src/main/java/com/pietschy/gwt/pectin/rebind/BeanModelProviderFactoryGenerator.java
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/rebind/BeanModelProviderFactoryGenerator.java	(revision 0)
+++ src/main/java/com/pietschy/gwt/pectin/rebind/BeanModelProviderFactoryGenerator.java	(revision 0)
@@ -0,0 +1,143 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.rebind;
+
+import java.io.PrintWriter;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+import com.google.gwt.core.ext.Generator;
+import com.google.gwt.core.ext.GeneratorContext;
+import com.google.gwt.core.ext.TreeLogger;
+import com.google.gwt.core.ext.UnableToCompleteException;
+import com.google.gwt.core.ext.typeinfo.JClassType;
+import com.google.gwt.core.ext.typeinfo.NotFoundException;
+import com.google.gwt.core.ext.typeinfo.TypeOracle;
+import com.google.gwt.user.rebind.ClassSourceFileComposerFactory;
+import com.google.gwt.user.rebind.SourceWriter;
+import com.pietschy.gwt.pectin.client.bean.BeanDescriptor;
+import com.pietschy.gwt.pectin.client.bean.BeanModelProvider;
+import com.pietschy.gwt.pectin.client.bean.BeanModelProviderFactory;
+import com.pietschy.gwt.pectin.client.bean.Beans;
+import com.pietschy.gwt.pectin.client.bean.NestedBeanDescriptor;
+
+/**
+ * the {@link Generator} to generate the implementation of {@link BeanModelProviderFactory} as well as {@link BeanDescriptor} for all types that are
+ * declared through a {@link Beans} annotation.
+ */
+public class BeanModelProviderFactoryGenerator extends Generator {
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public String generate(TreeLogger logger, GeneratorContext context, String typeName) throws UnableToCompleteException {
+        BeanModelProviderCreator binder = new BeanModelProviderCreator(logger, context, typeName);
+
+        try {
+            // final all beans that are marked by @Beans
+            Set<JClassType> beans = new HashSet<JClassType>();
+            JClassType[] types = context.getTypeOracle().getTypes();
+            for (JClassType type : types) {
+                beans.addAll(getDeclaredBean(context.getTypeOracle(), type));
+            }
+
+            final String genPackageName = BeanModelProviderFactory.class.getPackage().getName();
+            final String genClassName = "BeanModelProviderFactoryImpl";
+
+            ClassSourceFileComposerFactory composer = new ClassSourceFileComposerFactory(genPackageName, genClassName);
+            composer.setSuperclass(BeanModelProviderFactory.class.getCanonicalName());
+            composer.addImport(BeanDescriptor.class.getName());
+            composer.addImport(BeanModelProvider.class.getName());
+            composer.addImport(Map.class.getName());
+            composer.addImport(HashMap.class.getName());
+            composer.addImport(NestedBeanDescriptor.class.getName());
+
+            PrintWriter pw = context.tryCreate(logger, genPackageName, genClassName);
+
+            if (pw != null) {
+                SourceWriter sw = composer.createSourceWriter(context, pw);
+
+                sw.println("private Map<String, BeanDescriptor> cache;");
+                sw.println("public BeanDescriptor getBeanDescriptor(Class<?> klass) {");
+                sw.indent();
+                sw.println("String className = klass.getName();");
+                sw.println("if (cache == null) {");
+                sw.indentln("cache = new HashMap<String, BeanDescriptor>();");
+                sw.println("}");
+                sw.println("BeanDescriptor result = cache.get(className);");
+                sw.println("if (result == null) {");
+                sw.indent();
+                StringBuffer sb = new StringBuffer();
+                boolean start = true;
+                for (JClassType bean : beans) {
+                    String name = binder.createBeanDescriptor(bean);
+
+                    if (!start) {
+                        sw.print(" else ");
+                    } else {
+                        start = false;
+                    }
+                    sw.println("if (" + bean.getQualifiedSourceName() + ".class.getName().equals(className)) {");
+                    sw.indentln("result = new NestedBeanDescriptor(new " + name + "());");
+                    sw.indentln("cache.put(" + bean.getQualifiedSourceName() + ".class.getName(), result);");
+                    sw.indentln("return result;");
+                    sw.println("}");
+                }
+                sw.outdent();
+                sw.println("} else {");
+                sw.indent();
+                sw.println("return result;");
+                sw.outdent();
+                sw.println("}");
+                sw.println("throw new IllegalStateException(\"Unable to find a BeanDescriptor for class \" + className);");
+                sw.outdent();
+                sw.println("}");
+                sw.println(sb.toString());
+                sw.commit(logger);
+            }
+
+            return composer.getCreatedClassName();
+
+        } catch (Exception e) {
+            logger.log(TreeLogger.ERROR, "Class " + typeName + " not found.", e);
+            throw new UnableToCompleteException();
+        }
+
+    }
+
+    /**
+     * returns all types that are declared with the {@link Beans} annotation on the given type.
+     * 
+     * @param oracle the {@link TypeOracle} to resolve the beans.
+     * @param type the type to inspect.
+     * @return all types that are declared with the {@link Beans} annotation on the given type.
+     * @throws NotFoundException if an error occured.
+     */
+    private Set<JClassType> getDeclaredBean(TypeOracle oracle, JClassType type) throws NotFoundException {
+        Set<JClassType> result = new HashSet<JClassType>();
+        Beans pojo = type.getAnnotation(Beans.class);
+        if (pojo != null) {
+            for (Class<?> klass : pojo.value()) {
+                result.add(oracle.getType(klass.getCanonicalName()));
+            }
+        }
+        return result;
+    }
+
+}
Index: src/main/java/com/pietschy/gwt/pectin/rebind/BeanModelProviderCreator.java
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/rebind/BeanModelProviderCreator.java	(revision 640)
+++ src/main/java/com/pietschy/gwt/pectin/rebind/BeanModelProviderCreator.java	(working copy)
@@ -16,6 +16,12 @@
 
 package com.pietschy.gwt.pectin.rebind;
 
+import java.io.PrintWriter;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Set;
+
 import com.google.gwt.core.ext.GeneratorContext;
 import com.google.gwt.core.ext.TreeLogger;
 import com.google.gwt.core.ext.typeinfo.JClassType;
@@ -23,14 +29,15 @@
 import com.google.gwt.core.ext.typeinfo.TypeOracle;
 import com.google.gwt.user.rebind.ClassSourceFileComposerFactory;
 import com.google.gwt.user.rebind.SourceWriter;
-import com.pietschy.gwt.pectin.client.bean.*;
+import com.pietschy.gwt.pectin.client.bean.BeanDescriptor;
+import com.pietschy.gwt.pectin.client.bean.CollectionPropertyDescriptor;
+import com.pietschy.gwt.pectin.client.bean.DefaultPropertyDescriptor;
+import com.pietschy.gwt.pectin.client.bean.NestedTypes;
+import com.pietschy.gwt.pectin.client.bean.PropertyDescriptor;
+import com.pietschy.gwt.pectin.client.bean.ReadOnlyPropertyException;
+import com.pietschy.gwt.pectin.client.bean.TargetBeanIsNullException;
+import com.pietschy.gwt.pectin.client.bean.UnknownPropertyException;
 
-import java.io.PrintWriter;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.Set;
-
 /**
  * TODO: Improve error messages when a property is referenced that hasn't been annotated with @NestedBean.
  */
@@ -49,7 +56,51 @@
       this.typeOracle = context.getTypeOracle();
       this.typeName = typeName;
    }
+   
+   /**
+    * Generate a {@link BeanDescriptor} for the given type.
+    * @param beanType the type to generate a descriptor for.
+    * @return the type of the genarated {@link BeanDescriptor}.
+    * @throws Exception if an error occured.
+    */
+   public String createBeanDescriptor(JClassType beanType) throws Exception {
+       final String genPackageName = beanType.getPackage().getName();
+       final String genClassName = "BeanDescriptor_" + beanType.getQualifiedSourceName().replace(".", "_");
 
+       ClassSourceFileComposerFactory composer = new ClassSourceFileComposerFactory(genPackageName, genClassName);
+       composer.addImport(PropertyDescriptor.class.getName());
+       composer.addImport(DefaultPropertyDescriptor.class.getName());
+       composer.addImport(CollectionPropertyDescriptor.class.getName());
+       composer.addImport(UnknownPropertyException.class.getName());
+       composer.addImport(TargetBeanIsNullException.class.getName());
+       composer.addImport(ReadOnlyPropertyException.class.getName());
+       composer.addImplementedInterface(BeanDescriptor.class.getCanonicalName());
+       PrintWriter pw = context.tryCreate(logger, genPackageName, genClassName);
+
+       if (pw != null) {
+           Writer writer = new Writer(composer.createSourceWriter(context, pw));
+
+           BeanInfo beanInfo = new BeanInfo(typeOracle, beanType, Collections.<Class>emptySet());
+
+           writer.indent();
+
+           writer.println();
+
+           // e.g. private PropertyKey key_firstName = new DefaultPropertyKey(...);
+           generateDescriptorVars(writer, beanInfo);
+
+           writer.println();
+
+           // e.g. private BeanPropertyAccessor accessor_a_package_Class = new BeanPropertyAccessor(){...};
+           generateGetPropertyDescriptorMethod(writer, beanInfo);
+
+           writer.commit(logger);
+
+       }
+       return composer.getCreatedClassName();
+     }
+
+   
    public String createProvider()
    {
       try
Index: src/main/java/com/pietschy/gwt/pectin/client/bean/BeanDescriptor.java
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/client/bean/BeanDescriptor.java	(revision 0)
+++ src/main/java/com/pietschy/gwt/pectin/client/bean/BeanDescriptor.java	(revision 0)
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean;
+
+/**
+ * A class that can give description about properties of a bean.
+ */
+public interface BeanDescriptor {
+
+    /**
+     * returns  the {@link PropertyDescriptor} of the property at the given path.
+     * @param path the path of the property.
+     * @return the {@link PropertyDescriptor} of the property at the given path.
+     */
+    PropertyDescriptor getPropertyDescriptor(String path);
+}
Index: src/main/java/com/pietschy/gwt/pectin/client/bean/NestedBeanDescriptor.java
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/client/bean/NestedBeanDescriptor.java	(revision 0)
+++ src/main/java/com/pietschy/gwt/pectin/client/bean/NestedBeanDescriptor.java	(revision 0)
@@ -0,0 +1,114 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ * 
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean;
+
+
+/**
+ * a {@link BeanModelProviderFactory} that will use the {@link BeanModelProviderFactory} to be able to resolved nested properties.
+ */
+public class NestedBeanDescriptor implements BeanDescriptor {
+
+    /**
+     * the base {@link BeanDescriptor}.
+     */
+    private final BeanDescriptor baseBeanDescriptor;
+
+    /**
+     * Constructor.
+     * 
+     * @param baseBeanDescriptorFactory the base {@link BeanIntrospector}.
+     */
+    public NestedBeanDescriptor(BeanDescriptor baseBeanDescriptor) {
+        this.baseBeanDescriptor = baseBeanDescriptor;
+    }
+    
+    /**
+     * A {@link PropertyDescriptor} that handles nested properties.
+     */
+    public static class NestedPropertyDescriptor extends AbstractPropertyDescriptor {
+
+        /**
+         * the simple {@link PropertyDescriptor} that can work on the objects. 
+         */
+        private final PropertyDescriptor lastDescriptor;
+        
+        public NestedPropertyDescriptor(final String fullPath, final String parentPath, final String propertyName, final PropertyDescriptor lastDescriptor) {
+            super(fullPath, parentPath, propertyName, lastDescriptor.getBeanType(), lastDescriptor.isMutable());
+            this.lastDescriptor = lastDescriptor;
+        }
+        
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public Class getElementType() throws NotCollectionPropertyException {
+            return lastDescriptor.getElementType();
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public Class getValueType() {
+            return lastDescriptor.getValueType();
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public boolean isCollection() {
+            return lastDescriptor.isCollection();
+        }
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public Object readProperty(Object bean) {
+            return lastDescriptor.readProperty(bean);
+        }
+
+
+        /**
+         * {@inheritDoc}
+         */
+        @Override
+        public void writeProperty(Object bean, Object value) throws ReadOnlyPropertyException, TargetBeanIsNullException {
+            lastDescriptor.writeProperty(bean, value);
+        }
+
+        
+    }
+
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public PropertyDescriptor getPropertyDescriptor(String path) {
+        final String[] propertiesPath = path.split("\\.");
+        if(propertiesPath.length == 1) {
+            return baseBeanDescriptor.getPropertyDescriptor(path);
+        }
+        final String finalProperty = propertiesPath[propertiesPath.length - 1];
+        BeanDescriptor currentBeanDescriptor = baseBeanDescriptor;
+        for (int i = 0; i < propertiesPath.length - 1; i++) {
+            final String currentProperty = propertiesPath[i];
+            final PropertyDescriptor propertyDescriptor = currentBeanDescriptor.getPropertyDescriptor(currentProperty);
+            currentBeanDescriptor = BeanModelProviderFactory.get().getBeanDescriptor(propertyDescriptor.getValueType());
+        }
+        return new NestedPropertyDescriptor(path, path.substring(0, path.lastIndexOf('.')), finalProperty, currentBeanDescriptor.getPropertyDescriptor(finalProperty));
+    }
+}
Index: src/main/java/com/pietschy/gwt/pectin/client/bean/DelegatingBeanModelProvider.java
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/client/bean/DelegatingBeanModelProvider.java	(revision 0)
+++ src/main/java/com/pietschy/gwt/pectin/client/bean/DelegatingBeanModelProvider.java	(revision 0)
@@ -0,0 +1,47 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean;
+
+/**
+ * A {@link BeanModelProvider} that use a given {@link BeanIntrospector}.
+ */
+public class DelegatingBeanModelProvider<B> extends BeanModelProvider<B> {
+
+    
+    /**
+     * the factory to build {@link PropertyDescriptor}.
+     */
+    final BeanDescriptor beanDescriptor;
+    
+    /**
+     * Constructor.
+     *
+     * @param beanDescriptor
+     * the factory to build {@link PropertyDescriptor}.
+     */
+    protected DelegatingBeanModelProvider(final BeanDescriptor beanDescriptor) {
+        this.beanDescriptor = beanDescriptor;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
+    @Override
+    public PropertyDescriptor getPropertyDescriptor(String path) {
+        return beanDescriptor.getPropertyDescriptor(path);
+    }
+
+}
Index: src/main/java/com/pietschy/gwt/pectin/client/bean/Beans.java
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/client/bean/Beans.java	(revision 0)
+++ src/main/java/com/pietschy/gwt/pectin/client/bean/Beans.java	(revision 0)
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * This annotation can be added to any class declarations
+ * to let the generator know types that should be exposed.
+ * <p>
+ * For example, the following usage will allows to use {@link BeanModelProviderFactory} with the Address class.
+ * <pre>
+ * &#064;Beans({Address.class})
+ * public interface BeanDeclaration{}
+ * </pre>
+ */
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.TYPE)
+public @interface Beans
+{
+   Class<?>[] value();
+}
\ No newline at end of file
Index: src/main/java/com/pietschy/gwt/pectin/client/bean/BeanModelProviderFactory.java
===================================================================
--- src/main/java/com/pietschy/gwt/pectin/client/bean/BeanModelProviderFactory.java	(revision 0)
+++ src/main/java/com/pietschy/gwt/pectin/client/bean/BeanModelProviderFactory.java	(revision 0)
@@ -0,0 +1,73 @@
+/*
+ * Copyright 2010 Benjamin Lerman
+ *
+ * Licensed 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 com.pietschy.gwt.pectin.client.bean;
+
+import com.google.gwt.core.client.GWT;
+
+/**
+ * Returns {@link BeanModelProvider} for java beans.
+ */
+public abstract class BeanModelProviderFactory {
+
+    private static BeanModelProviderFactory instance;
+
+    /**
+     * Returns the singleton bean model provider factory.
+     * 
+     * @return the singleton instance
+     */
+    public static BeanModelProviderFactory get() {
+        if (instance == null) {
+            if (GWT.isClient()) {
+                instance = GWT.create(BeanModelProviderFactory.class);
+            }
+        }
+        return instance;
+    }
+
+    /**
+     * Returns the {@link BeanModelProvider} for the given class.
+     * 
+     * @param bean the bean class
+     * @return the {@link BeanModelProvider}
+     */
+    public <B> BeanModelProvider<B> getBeanModelProvider(Class<B> beanClass) {
+        return new DelegatingBeanModelProvider<B>(getBeanDescriptor(beanClass));
+    }
+
+    /**
+     * Returns the {@link BeanIntrospector} for the given bean.
+     * 
+     * @param bean the bean class
+     * @return the {@link BeanIntrospector}
+     */
+    public abstract BeanDescriptor getBeanDescriptor(Class<?> beanClass);
+    
+    /**
+     * Returns the {@link BeanModelProvider} for the given bean.
+     * 
+     * @param bean the bean class
+     * @param autoCommit whether to autocommit the changes.
+     * 
+     * @return the {@link BeanModelProvider}
+     */
+    public <B> BeanModelProvider<B> getBeanModelProvider(Class<B> bean, boolean autoCommit) {
+        BeanModelProvider<B> result = getBeanModelProvider(bean);
+        result.setAutoCommit(true);
+        return result;
+    }
+
+}
