You are viewing a plain text version of this content. The canonical link for it is here.
Posted to server-dev@james.apache.org by do...@apache.org on 2013/08/21 16:08:29 UTC

svn commit: r1516164 [2/20] - in /james/hupa/trunk: ./ client/ client/src/main/java/com/ client/src/main/java/com/google/ client/src/main/java/com/google/web/ client/src/main/java/com/google/web/bindery/ client/src/main/java/com/google/web/bindery/requ...

Added: james/hupa/trunk/client/src/main/java/com/google/web/bindery/requestfactory/server/ResolverServiceLayer.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/com/google/web/bindery/requestfactory/server/ResolverServiceLayer.java?rev=1516164&view=auto
==============================================================================
--- james/hupa/trunk/client/src/main/java/com/google/web/bindery/requestfactory/server/ResolverServiceLayer.java (added)
+++ james/hupa/trunk/client/src/main/java/com/google/web/bindery/requestfactory/server/ResolverServiceLayer.java Wed Aug 21 14:08:19 2013
@@ -0,0 +1,263 @@
+/*
+ * Copyright 2010 Google Inc.
+ * 
+ * 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.google.web.bindery.requestfactory.server;
+
+import com.google.gwt.dev.asm.Type;
+import com.google.web.bindery.autobean.vm.impl.TypeUtils;
+import com.google.web.bindery.requestfactory.shared.BaseProxy;
+import com.google.web.bindery.requestfactory.shared.ProxyFor;
+import com.google.web.bindery.requestfactory.shared.ProxyForName;
+import com.google.web.bindery.requestfactory.shared.RequestContext;
+import com.google.web.bindery.requestfactory.shared.RequestFactory;
+import com.google.web.bindery.requestfactory.shared.Service;
+import com.google.web.bindery.requestfactory.shared.ServiceName;
+import com.google.web.bindery.requestfactory.vm.impl.Deobfuscator;
+import com.google.web.bindery.requestfactory.vm.impl.OperationKey;
+
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Set;
+
+/**
+ * Implements all of the resolution methods in ServiceLayer.
+ */
+final class ResolverServiceLayer extends ServiceLayerDecorator {
+
+  private static Deobfuscator deobfuscator;
+
+  private static synchronized void updateDeobfuscator(Class<? extends RequestFactory> clazz,
+      ClassLoader resolveClassesWith) {
+    Deobfuscator.Builder builder = Deobfuscator.Builder.load(clazz, resolveClassesWith);
+    if (deobfuscator != null) {
+      builder.merge(deobfuscator);
+    }
+    deobfuscator = builder.build();
+  }
+
+  @Override
+  public ClassLoader getDomainClassLoader() {
+    return Thread.currentThread().getContextClassLoader();
+  }
+
+  @Override
+  public Class<? extends BaseProxy> resolveClass(String typeToken) {
+    String deobfuscated = deobfuscator.getTypeFromToken(typeToken);
+    if (deobfuscated == null) {
+      die(null, "No type for token %s", typeToken);
+    }
+
+    return forName(deobfuscated).asSubclass(BaseProxy.class);
+  }
+
+  @Override
+  public <T> Class<? extends T> resolveClientType(Class<?> domainClass, Class<T> clientClass,
+      boolean required) {
+    if (List.class.isAssignableFrom(domainClass)) {
+      return List.class.asSubclass(clientClass);
+    }
+    if (Set.class.isAssignableFrom(domainClass)) {
+      return Set.class.asSubclass(clientClass);
+    }
+    if (TypeUtils.isValueType(domainClass)) {
+      return domainClass.asSubclass(clientClass);
+    }
+    
+    List<Class<?>> classes = new ArrayList<Class<?>>();
+    Class<?> clazz = domainClass;
+    while (clazz != null) {
+      classes.add(clazz);
+      clazz = clazz.getSuperclass();
+    }
+    classes.addAll(Arrays.asList(domainClass.getInterfaces()));
+    
+    for (Class<?> toSearch : classes) {
+      List<String> clientTypes = deobfuscator.getClientProxies(toSearch.getName());
+      if (clientTypes != null) {
+        for (String clientType : clientTypes) {
+          Class<?> proxy = forName(clientType);
+          if (clientClass.isAssignableFrom(proxy)) {
+            return proxy.asSubclass(clientClass);
+          }
+        }
+      }
+    }
+    
+    if (required) {
+      die(null, "The domain type %s cannot be sent to the client", domainClass.getCanonicalName());
+    }
+    return null;
+  }
+
+  @Override
+  public Class<?> resolveDomainClass(Class<?> clazz) {
+    if (List.class.equals(clazz)) {
+      return List.class;
+    } else if (Set.class.equals(clazz)) {
+      return Set.class;
+    } else if (BaseProxy.class.isAssignableFrom(clazz)) {
+      ProxyFor pf = clazz.getAnnotation(ProxyFor.class);
+      if (pf != null) {
+        return pf.value();
+      }
+      ProxyForName pfn = clazz.getAnnotation(ProxyForName.class);
+      if (pfn != null) {
+        Class<?> toReturn = forName(pfn.value());
+        return toReturn;
+      }
+    }
+    return die(null, "Could not resolve a domain type for client type %s", clazz.getCanonicalName());
+  }
+
+  @Override
+  public Method resolveDomainMethod(String operation) {
+    /*
+     * The validator has already determined the mapping from the RequsetContext
+     * method to a domain method signature. We'll reuse this calculation instead
+     * of iterating over all methods.
+     */
+    String domainDescriptor = deobfuscator.getDomainMethodDescriptor(operation);
+
+    if (domainDescriptor == null) {
+      return die(null, "No domain method descriptor is mapped to operation %s", operation);
+    }
+
+    Class<?>[] domainArgs = getArgumentTypes(domainDescriptor);
+    Class<? extends RequestContext> requestContext = getTop().resolveRequestContext(operation);
+    Class<?> serviceImplementation = getTop().resolveServiceClass(requestContext);
+
+    // Request<FooProxy> someMethod(int a, double b, FooProxy c);
+    Method requestContextMethod = getTop().resolveRequestContextMethod(operation);
+
+    Throwable ex;
+    try {
+      return serviceImplementation.getMethod(requestContextMethod.getName(), domainArgs);
+    } catch (SecurityException e) {
+      ex = e;
+    } catch (NoSuchMethodException e) {
+      ex = e;
+    }
+
+    return die(ex,
+        "Could not find method in implementation %s matching descriptor %s for operation %s",
+        serviceImplementation.getCanonicalName(), domainDescriptor, operation);
+  }
+
+  @Override
+  public Class<? extends RequestContext> resolveRequestContext(String operation) {
+    String requestContextClass = deobfuscator.getRequestContext(operation);
+    if (requestContextClass == null) {
+      die(null, "No RequestContext for operation %s", operation);
+    }
+    return forName(requestContextClass).asSubclass(RequestContext.class);
+  }
+
+  @Override
+  public Method resolveRequestContextMethod(String operation) {
+    Class<?> searchIn = getTop().resolveRequestContext(operation);
+    String methodName = deobfuscator.getRequestContextMethodName(operation);
+    String descriptor = deobfuscator.getRequestContextMethodDescriptor(operation);
+    Class<?>[] params = getArgumentTypes(descriptor);
+    try {
+      return searchIn.getMethod(methodName, params);
+    } catch (NoSuchMethodException ex) {
+      return report("Could not locate %s operation %s", RequestContext.class.getSimpleName(),
+          operation);
+    }
+  }
+
+  @Override
+  public Class<? extends RequestFactory> resolveRequestFactory(String binaryName) {
+    Class<? extends RequestFactory> toReturn = forName(binaryName).asSubclass(RequestFactory.class);
+    updateDeobfuscator(toReturn, getTop().getDomainClassLoader());
+    return toReturn;
+  }
+
+  @Override
+  public Class<?> resolveServiceClass(Class<? extends RequestContext> requestContextClass) {
+    Class<?> searchIn = null;
+    Service s = requestContextClass.getAnnotation(Service.class);
+    if (s != null) {
+      searchIn = s.value();
+    }
+    ServiceName sn = requestContextClass.getAnnotation(ServiceName.class);
+    if (sn != null) {
+      searchIn = forName(sn.value());
+    }
+    if (searchIn == null) {
+      die(null, "The %s type %s did not specify a service type", RequestContext.class
+          .getSimpleName(), requestContextClass.getCanonicalName());
+    }
+    return searchIn;
+  }
+
+  @Override
+  public String resolveTypeToken(Class<? extends BaseProxy> clazz) {
+    return OperationKey.hash(clazz.getName());
+  }
+
+  /**
+   * Call {@link Class#forName(String)} and report any errors through
+   * {@link #die()}.
+   */
+  private Class<?> forName(String name) {
+    try {
+      return Class.forName(name, false, getTop().getDomainClassLoader());
+    } catch (ClassNotFoundException e) {
+      return die(e, "Could not locate class %s", name);
+    }
+  }
+
+  private Class<?>[] getArgumentTypes(String descriptor) {
+    Type[] types = Type.getArgumentTypes(descriptor);
+    Class<?>[] params = new Class<?>[types.length];
+    for (int i = 0, j = types.length; i < j; i++) {
+      params[i] = getClass(types[i]);
+    }
+    return params;
+  }
+
+  private Class<?> getClass(Type type) {
+    switch (type.getSort()) {
+      case Type.BOOLEAN:
+        return boolean.class;
+      case Type.BYTE:
+        return byte.class;
+      case Type.CHAR:
+        return char.class;
+      case Type.DOUBLE:
+        return double.class;
+      case Type.FLOAT:
+        return float.class;
+      case Type.INT:
+        return int.class;
+      case Type.LONG:
+        return long.class;
+      case Type.OBJECT:
+        return forName(type.getClassName());
+      case Type.SHORT:
+        return short.class;
+      case Type.VOID:
+        return void.class;
+      case Type.ARRAY:
+        return die(null, "Unsupported Type used in operation descriptor %s", type.getDescriptor());
+      default:
+        // Error in this switch statement
+        return die(null, "Unhandled Type: %s", type.getDescriptor());
+    }
+  }
+}

Modified: james/hupa/trunk/client/src/main/java/org/apache/hupa/Hupa.gwt.xml
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/Hupa.gwt.xml?rev=1516164&r1=1516163&r2=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/Hupa.gwt.xml (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/Hupa.gwt.xml Wed Aug 21 14:08:19 2013
@@ -19,6 +19,17 @@
   <!-- Inherit the core Web Toolkit stuff.                        -->
   <inherits name='com.google.gwt.user.User'/>
   <inherits name="com.google.gwt.i18n.I18N"/> 
+  <!-- inherits Logging module -->
+  <inherits name="com.google.gwt.logging.Logging"/>
+  <set-property name="gwt.logging.enabled" value="TRUE"/>
+  <set-property name="gwt.logging.logLevel" value="FINE"/>
+  <set-property name="gwt.logging.consoleHandler" value="DISABLED"/>
+  <set-property name="gwt.logging.developmentModeHandler" value="ENABLED"/>
+  <set-property name="gwt.logging.firebugHandler" value="ENABLED"/>
+  <set-property name="gwt.logging.hasWidgetsHandler" value="DISABLED"/>
+  <set-property name="gwt.logging.popupHandler" value="DISABLED"/>
+  <set-property name="gwt.logging.systemHandler" value="ENABLED"/>
+  <set-property name="gwt.logging.simpleRemoteHandler" value="DISABLED"/>
   <!-- Hupa modules -->  
   <inherits name='org.apache.hupa.Shared'/> 
   <inherits name='org.apache.hupa.Widgets'/> 
@@ -28,9 +39,14 @@
   <inherits name='com.google.gwt.gen2.commonwidget.CommonWidget' />
   <inherits name='com.google.gwt.gen2.table.override.Override'/>
   <inherits name='com.google.gwt.gen2.table.ScrollTable'/>
-  <inherits name='net.customware.gwt.dispatch.Dispatch' />
-  <inherits name='net.customware.gwt.presenter.Presenter' />
+  <inherits name="com.google.gwt.activity.Activity"/>
+  <inherits name="com.google.gwt.place.Place"/>
   <inherits name="com.google.gwt.inject.Inject"/>
+  
+  <inherits name="com.google.gwt.cell.Cell"/>
+  <inherits name="com.google.gwt.editor.Editor"/>
+  <inherits name="com.google.gwt.resources.Resources" />
+  
   <inherits name="gwtupload.GWTUpload"/>
   <inherits name="eu.maydu.gwt.validation.ValidationLibrary"/>
   <inherits name='com.allen_sauer.gwt.dnd.gwt-dnd'/>
@@ -41,11 +57,11 @@
 <!--   <inherits name='com.google.gwt.user.theme.standard.Standard'/> -->
 <!--   <inherits name='com.google.gwt.user.theme.chrome.Chrome'/> -->
 <!--   <inherits name='com.google.gwt.user.theme.dark.Dark'/>     -->
-  <inherits name='com.google.gwt.user.theme.clean.Clean'/>    
+ <!--  <inherits name='com.google.gwt.user.theme.clean.Clean'/>    --> 
+  
   
   <!-- CSS loaded asynchronously -->
-  <stylesheet src="../Hupa.css"/>
-  <stylesheet src="Upload.css"/>
+  <stylesheet src="../styles.css"/>
   
   <!--  xsiframe would be the default in gwt soon -->
   <add-linker name="xsiframe"/>

Modified: james/hupa/trunk/client/src/main/java/org/apache/hupa/HupaProd.gwt.xml
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/HupaProd.gwt.xml?rev=1516164&r1=1516163&r2=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/HupaProd.gwt.xml (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/HupaProd.gwt.xml Wed Aug 21 14:08:19 2013
@@ -26,7 +26,7 @@
 
   <!-- Set the languages to compile -->
   <!-- It multiplies the number of permutations -->
-  <extend-property name="locale" values="es,de"/> 
+  <!-- <extend-property name="locale" values="es,de"/>  -->
   <set-configuration-property name="locale.useragent" value="Y"/>
 
   <!-- Compile for all browsers -->

Modified: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/Hupa.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/Hupa.java?rev=1516164&r1=1516163&r2=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/Hupa.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/Hupa.java Wed Aug 21 14:08:19 2013
@@ -19,32 +19,39 @@
 
 package org.apache.hupa.client;
 
-import net.customware.gwt.presenter.client.place.PlaceManager;
-
-import org.apache.hupa.client.gin.HupaGinjector;
-import org.apache.hupa.client.mvp.AppPresenter;
+import org.apache.hupa.client.ioc.AppGinjector;
 
 import com.google.gwt.core.client.EntryPoint;
 import com.google.gwt.core.client.GWT;
+import com.google.gwt.core.client.GWT.UncaughtExceptionHandler;
 import com.google.gwt.user.client.DOM;
 import com.google.gwt.user.client.ui.RootPanel;
 
-public class Hupa implements EntryPoint{
-    private final HupaGinjector injector = GWT.create(HupaGinjector.class);
-    
-    public void onModuleLoad() {
-        // remove the loading message from the browser
-        com.google.gwt.user.client.Element loading = DOM.getElementById("loading");
-
-        DOM.removeChild(RootPanel.getBodyElement(), loading);
-
-        AppPresenter aPres = injector.getAppPresenter();
-        aPres.bind();
-       
-        RootPanel.get().add(aPres.getDisplay().asWidget());
-
-        PlaceManager placeManager = injector.getPlaceManager();
-        placeManager.fireCurrentPlace();
-    }
+public class Hupa implements EntryPoint {
+	@Override
+	public void onModuleLoad() {
+		handleExceptionsAsync();
+		initApp();
+	}
+
+	private void initApp() {
+		replaceLoading();
+		injector.getHupaController().start();
+	}
+
+	private void handleExceptionsAsync() {
+		GWT.setUncaughtExceptionHandler(new UncaughtExceptionHandler() {
+			public void onUncaughtException(Throwable e) {
+				e.printStackTrace();
+			}
+		});
+	}
+
+	private void replaceLoading() {
+		DOM.removeChild(RootPanel.getBodyElement(),
+				DOM.getElementById("loading"));
+	}
+
+	private final AppGinjector injector = GWT.create(AppGinjector.class);
 
 }

Modified: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaCSS.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaCSS.java?rev=1516164&r1=1516163&r2=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaCSS.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaCSS.java Wed Aug 21 14:08:19 2013
@@ -26,6 +26,8 @@ import org.apache.hupa.widgets.WidgetsCS
  * CSS class names used in Hupa
  */
 public class HupaCSS extends WidgetsCSS {
+	
+	public static final String C_app_body="body";
     
     public static final String C_app_container ="Hupa";
 

Modified: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaConstants.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaConstants.java?rev=1516164&r1=1516163&r2=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaConstants.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaConstants.java Wed Aug 21 14:08:19 2013
@@ -19,14 +19,13 @@
 
 package org.apache.hupa.client;
 
-import com.google.gwt.i18n.client.Constants;
-
-import eu.maydu.gwt.validation.client.i18n.StandardValidationMessagesImpl;
 import gwtupload.client.IUploader.UploaderConstants;
 
 import org.apache.hupa.widgets.PagingOptionsConstants;
 import org.apache.hupa.widgets.editor.ToolbarConstants;
 
+import com.google.gwt.i18n.client.Constants;
+
 public interface HupaConstants extends Constants, UploaderConstants, PagingOptionsConstants, ToolbarConstants {
 
     public String usernameLabel();

Added: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaController.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaController.java?rev=1516164&view=auto
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaController.java (added)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HupaController.java Wed Aug 21 14:08:19 2013
@@ -0,0 +1,199 @@
+/****************************************************************
+ * 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.hupa.client;
+
+import org.apache.hupa.client.activity.NotificationActivity;
+import org.apache.hupa.client.activity.ToolBarActivity;
+import org.apache.hupa.client.activity.TopBarActivity;
+import org.apache.hupa.client.mapper.ActivityManagerInitializer;
+import org.apache.hupa.client.place.ComposePlace;
+import org.apache.hupa.client.place.ContactPlace;
+import org.apache.hupa.client.place.FolderPlace;
+import org.apache.hupa.client.place.HupaPlace;
+import org.apache.hupa.client.place.SettingPlace;
+import org.apache.hupa.client.rf.CheckSessionRequest;
+import org.apache.hupa.client.rf.HupaRequestFactory;
+import org.apache.hupa.client.rf.IdleRequest;
+import org.apache.hupa.client.ui.HupaLayout;
+import org.apache.hupa.client.ui.HupaLayoutable;
+import org.apache.hupa.client.ui.LoginLayoutable;
+import org.apache.hupa.client.ui.LoginView;
+import org.apache.hupa.shared.domain.IdleAction;
+import org.apache.hupa.shared.domain.IdleResult;
+import org.apache.hupa.shared.domain.User;
+import org.apache.hupa.shared.events.LoginEvent;
+
+import com.google.gwt.core.client.GWT;
+import com.google.gwt.core.client.Scheduler;
+import com.google.gwt.core.client.Scheduler.ScheduledCommand;
+import com.google.gwt.dom.client.StyleInjector;
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.place.shared.Place;
+import com.google.gwt.place.shared.PlaceChangeEvent;
+import com.google.gwt.place.shared.PlaceController;
+import com.google.gwt.place.shared.PlaceHistoryHandler;
+import com.google.gwt.user.client.Timer;
+import com.google.gwt.user.client.ui.RootLayoutPanel;
+import com.google.inject.Inject;
+import com.google.web.bindery.requestfactory.shared.Receiver;
+import com.google.web.bindery.requestfactory.shared.ServerFailure;
+
+public class HupaController {
+
+	private static final int IDLE_INTERVAL = 15000;
+	private PlaceController placeController;
+	private PlaceHistoryHandler placeHistoryHandler;
+	@Inject private HupaLayoutable hupaLayout;
+	@Inject private HupaRequestFactory requestFactory;
+	@Inject private LoginLayoutable loginLayout;
+	@Inject private NotificationActivity.Displayable noticeRegion;
+	@Inject private TopBarActivity.Displayable topBar;
+	@Inject private ToolBarActivity.Displayable toolBar;
+	private EventBus eventBus;
+
+	private Timer noopTimer = new IdleTimer();
+
+	@Inject
+	public HupaController(PlaceController placeController, PlaceHistoryHandler placeHistoryHandler, EventBus eventBus,
+			ActivityManagerInitializer initializeActivityManagerByGin) {
+		this.placeController = placeController;
+		this.placeHistoryHandler = placeHistoryHandler;
+		this.eventBus = eventBus;
+		eventBus.addHandler(PlaceChangeEvent.TYPE, new PlaceChangHandler());
+	}
+
+	public void start() {
+		bindCss();
+		placeHistoryHandler.handleCurrentHistory();
+	}
+
+	private void bindCss() {
+		// TODO:replace with a more gentle approach
+		StyleInjector.inject(LoginView.Resources.INSTANCE.stylesheet().getText());
+	}
+
+	private final class PlaceChangHandler implements PlaceChangeEvent.Handler {
+		@Override
+		public void onPlaceChange(PlaceChangeEvent event) {
+			checkSession();
+			adjustLayout(event);
+		}
+	}
+
+	private void adjustLayout(PlaceChangeEvent event) {
+		Place place = event.getNewPlace();
+		if (place instanceof ComposePlace) {
+			ComposePlace here = (ComposePlace) place;
+			if (here.getParameters() != null) {
+				hupaLayout.switchTo(HupaLayout.LAYOUT_COMPOSE);
+			} else {
+				//FIXME using configure one
+				if(GWT.isProdMode()){
+					placeController.goTo(new FolderPlace("INBOX"));
+				}else{
+					placeController.goTo(new FolderPlace("Mock-Inbox"));
+				}
+			}
+		} else if (place instanceof ContactPlace) {
+			hupaLayout.switchTo(HupaLayout.LAYOUT_CONTACT);
+		}  else if (place instanceof SettingPlace) {
+			hupaLayout.switchTo(HupaLayout.LAYOUT_SETTING);
+		} else if(place instanceof HupaPlace){
+			hupaLayout.switchTo(HupaLayout.LAYOUT_MESSAGE);
+		}
+	}
+
+	private void checkSession() {
+		CheckSessionRequest checkSession = requestFactory.sessionRequest();
+		checkSession.getUser().fire(new Receiver<User>() {
+			@Override
+			public void onSuccess(User user) {
+				if (user == null) {
+					RootLayoutPanel.get().clear();
+					RootLayoutPanel.get().add(loginLayout.get());
+					noopTimer.cancel();
+				} else {
+					RootLayoutPanel.get().clear();
+					RootLayoutPanel.get().add(hupaLayout.get());
+					eventBus.fireEvent(new LoginEvent(user));
+					noopTimer.scheduleRepeating(IDLE_INTERVAL);
+				}
+			}
+
+			@Override
+			public void onFailure(ServerFailure error) {
+				RootLayoutPanel.get().clear();
+				RootLayoutPanel.get().add(loginLayout.get());
+				noopTimer.cancel();
+			}
+		});
+	}
+
+	public void showNotice(String html, int millis) {
+		noticeRegion.notice(html);
+		if (millis > 0)
+			hideNotice.schedule(millis);
+	}
+
+	public void showTopLoading(String message) {
+		topBar.showLoading(message);
+	}
+
+	public void hideTopLoading() {
+		Scheduler.get().scheduleDeferred(new ScheduledCommand() {
+			@Override
+			public void execute() {
+				topBar.hideLoading();
+			}
+		});
+	}
+
+	private final Timer hideNotice = new Timer() {
+		public void run() {
+			noticeRegion.hideNotification();
+		}
+	};
+
+	private class IdleTimer extends Timer {
+		boolean running = false;
+
+		public void run() {
+			if (!running) {
+				running = true;
+				IdleRequest idle = requestFactory.idleRequest();
+				IdleAction action = idle.create(IdleAction.class);
+				idle.idle(action).fire(new Receiver<IdleResult>() {
+					@Override
+					public void onSuccess(IdleResult response) {
+						running = false;
+						// check if the server is not supporting the Idle
+						// command. if so cancel this Timer
+						if (response.isSupported() == false) {
+							IdleTimer.this.cancel();
+						}
+						// Noop
+						// TODO: put code here to read new events from server
+						// (new messages ...)
+					}
+				});
+			}
+		}
+	}
+}

Copied: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/AppBaseActivity.java (from r1375909, james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HandlerRegistrationAdapter.java)
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/AppBaseActivity.java?p2=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/AppBaseActivity.java&p1=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HandlerRegistrationAdapter.java&r1=1375909&r2=1516164&rev=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/HandlerRegistrationAdapter.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/AppBaseActivity.java Wed Aug 21 14:08:19 2013
@@ -1,45 +1,63 @@
-/****************************************************************
- * 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.hupa.client;
-
-import com.google.gwt.event.shared.HandlerRegistration;
-
-
-/**
- * Class to act as Adapter between HandlerRegistration in gwt 1.6+ and gwt-incubator
- *
- */
-@SuppressWarnings("deprecation")
-public class HandlerRegistrationAdapter implements HandlerRegistration{
-    com.google.gwt.gen2.event.shared.HandlerRegistration registration;
-
-    public HandlerRegistrationAdapter(com.google.gwt.gen2.event.shared.HandlerRegistration registration) {
-        this.registration = registration;
-    }
-
-
-    /*
-     * (non-Javadoc)
-     * @see com.google.gwt.event.shared.HandlerRegistration#removeHandler()
-     */
-    public void removeHandler() {
-        registration.removeHandler();
-    }
-}
\ No newline at end of file
+/****************************************************************
+ * 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.hupa.client.activity;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.hupa.client.HupaController;
+import org.apache.hupa.client.rf.HupaRequestFactory;
+
+import com.google.gwt.activity.shared.AbstractActivity;
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.event.shared.HandlerRegistration;
+import com.google.gwt.place.shared.PlaceController;
+import com.google.inject.Inject;
+
+public abstract class AppBaseActivity extends AbstractActivity {
+
+	@Inject protected EventBus eventBus;
+	@Inject protected HupaController hc;
+	@Inject protected PlaceController pc;
+	@Inject protected HupaRequestFactory rf;
+
+	protected List<HandlerRegistration> registrations = new ArrayList<HandlerRegistration>();
+
+	@Override
+	public void onStop() {
+		for (HandlerRegistration registration : registrations) {
+			if(registration != null){
+				registration.removeHandler();	
+			}
+		}
+		registrations.clear();
+	}
+
+	protected void registerHandler(HandlerRegistration handlerRegistration) {
+		registrations.add(handlerRegistration);
+	}
+
+	public String mayStop() {
+		return null;
+	}
+
+	public void onCancel() {
+	}
+}

Added: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeActivity.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeActivity.java?rev=1516164&view=auto
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeActivity.java (added)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeActivity.java Wed Aug 21 14:08:19 2013
@@ -0,0 +1,483 @@
+/****************************************************************
+ * 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.hupa.client.activity;
+
+import gwtupload.client.IUploadStatus.Status;
+import gwtupload.client.IUploader;
+import gwtupload.client.IUploader.OnCancelUploaderHandler;
+import gwtupload.client.IUploader.OnFinishUploaderHandler;
+import gwtupload.client.IUploader.OnStatusChangedHandler;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+
+import org.apache.hupa.client.HupaController;
+import org.apache.hupa.client.place.ComposePlace;
+import org.apache.hupa.client.rf.SendForwardMessageRequest;
+import org.apache.hupa.client.rf.SendMessageRequest;
+import org.apache.hupa.client.rf.SendReplyMessageRequest;
+<<<<<<< HEAD
+import org.apache.hupa.client.ui.WidgetDisplayable;
+=======
+import org.apache.hupa.client.ui.MessagesCellTable;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+import org.apache.hupa.client.validation.EmailListValidator;
+import org.apache.hupa.shared.Util;
+import org.apache.hupa.shared.data.MessageAttachmentImpl;
+import org.apache.hupa.shared.domain.GenericResult;
+import org.apache.hupa.shared.domain.ImapFolder;
+import org.apache.hupa.shared.domain.Message;
+import org.apache.hupa.shared.domain.MessageAttachment;
+import org.apache.hupa.shared.domain.MessageDetails;
+import org.apache.hupa.shared.domain.SendForwardMessageAction;
+import org.apache.hupa.shared.domain.SendMessageAction;
+import org.apache.hupa.shared.domain.SendReplyMessageAction;
+import org.apache.hupa.shared.domain.SmtpMessage;
+import org.apache.hupa.shared.domain.User;
+import org.apache.hupa.shared.events.LoginEvent;
+import org.apache.hupa.shared.events.LoginEventHandler;
+<<<<<<< HEAD
+=======
+import org.apache.hupa.shared.events.MailToEvent;
+import org.apache.hupa.shared.events.MailToEventHandler;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+
+import com.google.gwt.activity.shared.Activity;
+import com.google.gwt.event.dom.client.ClickEvent;
+import com.google.gwt.event.dom.client.ClickHandler;
+import com.google.gwt.event.dom.client.HasClickHandlers;
+import com.google.gwt.event.shared.EventBus;
+<<<<<<< HEAD
+=======
+import com.google.gwt.storage.client.Storage;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+import com.google.gwt.user.client.History;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+import com.google.gwt.user.client.ui.HasHTML;
+import com.google.gwt.user.client.ui.HasText;
+<<<<<<< HEAD
+=======
+import com.google.gwt.user.client.ui.IsWidget;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+import com.google.gwt.user.client.ui.ListBox;
+import com.google.inject.Inject;
+import com.google.web.bindery.requestfactory.shared.Receiver;
+import com.google.web.bindery.requestfactory.shared.RequestContext;
+
+public class ComposeActivity extends AppBaseActivity {
+	@Inject private Displayable display;
+	@Inject private HupaController hupaController;
+	@Inject private TopBarActivity topBar;
+	private List<MessageAttachment> attachments = new ArrayList<MessageAttachment>();
+	private ComposePlace place;
+	private User user;
+
+	public Activity with(ComposePlace place) {
+		this.place = place;
+		return this;
+	}
+
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		container.setWidget(display.asWidget());
+		bindTo(eventBus);
+		fillHeader();
+	}
+
+	@Override
+	public String mayStop() {
+		super.mayStop();
+		if (noContent()) {
+			return null;
+		}
+		return null;
+//		return "Do you want to leave this page?"; TODO
+	}
+
+	@Override
+	public void onStop() {
+		super.onStop();
+	}
+
+	private boolean noContent() {
+		return "".equals(display.getMessage().getText()) && "".equals(display.getSubject().getText());
+	}
+
+	@Override
+	public void onCancel() {
+
+	}
+
+	private void fillHeader() {
+		if (place == null || place.getParameters() == null)
+			return;
+		if (user == null){
+			user = place.getParameters().getUser();
+		}
+		if(user == null){
+			user = topBar.getUser();
+		}
+		display.getFromList().addItem(user.getName());
+		if("new".equals(place.getToken())){
+			return;
+		}
+		Message oldMessage = place.getParameters().getOldmessage();
+		display.getMessageHTML().setHTML(
+				wrapMessage(oldMessage, place.getParameters().getOldDetails(), place.getToken()));
+		if ("forward".equals(place.getToken())) {
+			String subject = oldMessage.getSubject() != null ? oldMessage.getSubject().trim() : "";
+			if (!subject.toLowerCase().startsWith("fwd:")) {
+				subject = "Fwd: " + subject;
+			}
+			display.getSubject().setText(subject);
+		} else if ("reply".equals(place.getToken()) || "replyAll".equals(place.getToken())) {
+
+			String subject = oldMessage.getSubject() != null ? oldMessage.getSubject().trim() : "";
+			if (!subject.toLowerCase().startsWith("re:")) {
+				subject = "Re: " + subject;
+			}
+			if ("reply".equals(place.getToken())) {
+				display.getSubject().setText(subject);
+				if (oldMessage.getReplyto() != null && !oldMessage.getFrom().contains(oldMessage.getReplyto())) {
+					display.getTo().setText(oldMessage.getReplyto());
+				} else {
+					display.getTo().setText(oldMessage.getFrom());
+				}
+			} else if ("replyAll".equals(place.getToken())) {
+				ArrayList<String> list = new ArrayList<String>();
+				if (oldMessage.getReplyto() != null && !oldMessage.getFrom().contains(oldMessage.getReplyto()))
+					list.add(oldMessage.getReplyto());
+				if (oldMessage.getTo() != null)
+					list.addAll(oldMessage.getTo());
+				if (oldMessage.getCc() != null)
+					list.addAll(oldMessage.getCc());
+				list = removeEmailFromList(list, user.getName());
+				display.getCc().setText(Util.listToString(list));
+				if (oldMessage.getTo() != null) {
+					oldMessage.getTo().remove(user.getName());
+				}
+				display.getTo().setText(oldMessage.getFrom());
+			}
+		}
+	}
+
+	protected ArrayList<String> removeEmailFromList(List<String> list, String email) {
+		ArrayList<String> ret = new ArrayList<String>();
+		String regex = ".*<?\\s*" + email.trim() + "\\s*>?\\s*";
+		for (String e : list) {
+			if (!e.matches(regex)) {
+				ret.add(e);
+			}
+		}
+		return ret;
+	}
+	private static String generateHeader(Message message, String type) {
+		String ret = "<br>";
+		if (message != null) {
+			if (type.equals("forward")) {
+				ret += "--------- Forwarded message --------- <br>";
+				ret += "From: " + message.getFrom().replaceAll("<", "&lt;").replaceAll(">", "&gt;") + "<br>";
+				ret += "Date: " + message.getReceivedDate() + "<br>";
+				ret += "Subject: " + message.getSubject() + "<br>";
+				ArrayList<String> to = new ArrayList<String>();
+				to.addAll(message.getTo());
+				to.addAll(message.getCc());
+				ret += "To: " + Util.listToString(to).replaceAll("<", "&lt;").replaceAll(">", "&gt;") + "<br>";
+			} else if (type.equals("reply") || type.equals("replyAll")) {
+				ret += "On " + message.getReceivedDate();
+				ret += ", " + message.getFrom().replaceAll("<", "&lt;").replaceAll(">", "&gt;");
+				ret += ". wrote:<br>";
+			}
+		}
+		return ret + "<br>";
+	}
+	public static String wrapMessage(Message message, MessageDetails details, String type) {
+		String ret = "";
+		if (message != null) {
+			ret += generateHeader(message, type);
+		}
+		if (details != null && details.getText() != null && details.getText().length() > 0) {
+			ret += "<blockquote style='border-left: 1px solid rgb(204, 204, 204); margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;'>";
+			ret += details.getText();
+			ret += "</blockquote>";
+		}
+		return ret;
+	}
+	private void bindTo(EventBus eventBus) {
+		eventBus.addHandler(LoginEvent.TYPE, new LoginEventHandler() {
+			public void onLogin(LoginEvent event) {
+				user = event.getUser();
+			}
+		});
+		registerHandler(display.getSendClick().addClickHandler(sendClickHandler));
+		registerHandler(display.getCancelClick().addClickHandler(cancelClickHandler));
+
+		registerHandler(display.getCcClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.showCc();
+			}
+		}));
+		registerHandler(display.get_CcClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.hideCc();
+			}
+		}));
+		registerHandler(display.getBccClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.showBcc();
+			}
+		}));
+		registerHandler(display.get_BccClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.hideBcc();
+			}
+		}));
+		registerHandler(display.getReplyClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.showReply();
+			}
+		}));
+		registerHandler(display.get_ReplyClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.hideReply();
+			}
+		}));
+		registerHandler(display.getFollowupClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.showFollowup();
+			}
+		}));
+		registerHandler(display.get_FollowupClick().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				display.hideFollowup();
+			}
+		}));
+		registerHandler(display.getUploader().addOnStatusChangedHandler(onStatusChangedHandler));
+		registerHandler(display.getUploader().addOnFinishUploadHandler(onFinishUploadHandler));
+		registerHandler(display.getUploader().addOnCancelUploadHandler(onCancelUploadHandler));
+<<<<<<< HEAD
+=======
+
+		eventBus.addHandler(MailToEvent.TYPE, new MailToEventHandler(){
+
+			@Override
+			public void onMailTo(MailToEvent event) {
+				display.getTo().setText(event.getMailto());
+			}});
+		
+		fillSuggestList();
+		
+	}
+
+	private void fillSuggestList() {
+		Storage contactStore = Storage.getLocalStorageIfSupported();
+		if(contactStore != null){
+			String contactsString = contactStore.getItem(MessagesCellTable.CONTACTS_STORE);
+			if(contactsString != null){
+				display.fillContactList(contactsString.replace("[", "").replace("]", "").trim().split(","));	
+			}	
+		}
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+	}
+
+	private OnFinishUploaderHandler onFinishUploadHandler = new OnFinishUploaderHandler() {
+		public void onFinish(IUploader uploader) {
+			if (uploader.getStatus() == Status.SUCCESS) {
+				String name = uploader.getInputName();
+				MessageAttachment attachment = new MessageAttachmentImpl();
+				attachment.setName(name);
+				attachments.add(attachment);
+			}
+		}
+	};
+
+	private OnStatusChangedHandler onStatusChangedHandler = new OnStatusChangedHandler() {
+		public void onStatusChanged(IUploader uploader) {
+			// TODO buttons disabled
+			// Status stat = display.getUploader().getStatus();
+
+			// if (stat == Status.INPROGRESS)
+			// display.getSendEnable().setEnabled(false);
+			// else
+			// display.getSendEnable().setEnabled(true);
+		}
+	};
+
+	private OnCancelUploaderHandler onCancelUploadHandler = new OnCancelUploaderHandler() {
+		public void onCancel(IUploader uploader) {
+			for (Iterator<MessageAttachment> i = attachments.iterator(); i.hasNext();) {
+				MessageAttachment attachment = i.next();
+				if (attachment.getName().equals(uploader.getInputName()))
+					i.remove();
+			}
+		}
+	};
+
+	private ClickHandler cancelClickHandler = new ClickHandler() {
+		@Override
+		public void onClick(ClickEvent event) {
+			History.back();
+		}
+
+	};
+
+	protected ClickHandler sendClickHandler = new ClickHandler() {
+		public void onClick(ClickEvent event) {
+			if (!validate())
+				return;
+			hupaController.showTopLoading("Sending...");
+
+			if ("new".equals(place.getToken())) {
+				SendMessageRequest sendReq = rf.sendMessageRequest();
+				SendMessageAction sendAction = sendReq.create(SendMessageAction.class);
+				sendAction.setMessage(parseMessage(sendReq));
+				sendReq.send(sendAction).fire(new Receiver<GenericResult>() {
+					@Override
+					public void onSuccess(GenericResult response) {
+						afterSend(response);
+					}
+				});
+			} else if ("forward".equals(place.getToken())) {
+				// FIXME will get a NullPointerException given accessing
+				// directly from some URL like #/compose:forward
+				SendForwardMessageRequest req = rf.sendForwardMessageRequest();
+				SendForwardMessageAction action = req.create(SendForwardMessageAction.class);
+				action.setMessage(parseMessage(req));
+				ImapFolder f = req.create(ImapFolder.class);
+				f.setFullName(place.getParameters().getFolderName());
+				action.setFolder(f);
+				action.setUid(place.getParameters().getOldmessage().getUid());
+				req.send(action).fire(new Receiver<GenericResult>() {
+					@Override
+					public void onSuccess(GenericResult response) {
+						afterSend(response);
+					}
+				});
+			} else {
+				SendReplyMessageRequest replyReq = rf.sendReplyMessageRequest();
+				SendReplyMessageAction action = replyReq.create(SendReplyMessageAction.class);
+				action.setMessage(parseMessage(replyReq));
+				ImapFolder folder = replyReq.create(ImapFolder.class);
+				folder.setFullName(place.getParameters().getFolderName());
+				action.setFolder(folder);
+				action.setUid(place.getParameters().getOldmessage().getUid());
+				replyReq.send(action).fire(new Receiver<GenericResult>() {
+					@Override
+					public void onSuccess(GenericResult response) {
+						afterSend(response);
+					}
+				});
+			}
+		}
+	};
+
+	private boolean validate() {
+		// Don't trust only in view validation
+		return display.validate() && display.getTo().getText().trim().length() > 0
+				&& EmailListValidator.isValidAddressList(display.getTo().getText())
+				&& EmailListValidator.isValidAddressList(display.getCc().getText())
+				&& EmailListValidator.isValidAddressList(display.getBcc().getText());
+	}
+
+	private SmtpMessage parseMessage(RequestContext rc) {
+		SmtpMessage message = rc.create(SmtpMessage.class);
+		List<MessageAttachment> attaches = new ArrayList<MessageAttachment>();
+		for (MessageAttachment attach : attachments) {
+			MessageAttachment attachMent = rc.create(MessageAttachment.class);
+			attachMent.setName(attach.getName());
+			attachMent.setSize(attach.getSize());
+			attachMent.setContentType(attach.getContentType());
+			attaches.add(attachMent);
+		}
+		message.setFrom(display.getFromText());
+		message.setSubject(display.getSubject().getText());
+		message.setText(display.getMessageHTML().getHTML());
+		message.setMessageAttachments(attaches);
+		message.setTo(emailTextToArray(display.getTo().getText()));
+		message.setCc(emailTextToArray(display.getCc().getText()));
+		message.setBcc(emailTextToArray(display.getBcc().getText()));
+		return message;
+	}
+
+	private List<String> emailTextToArray(String emails) {
+		List<String> cc = new ArrayList<String>();
+		for (String ccRaw : emails.split("[,;]+")) {
+			String ccRecip = ccRaw.trim();
+			if (ccRecip.length() > 0) {
+				cc.add(ccRaw.trim());
+			}
+		}
+		return cc;
+	}
+
+	private void afterSend(GenericResult response) {
+		hupaController.hideTopLoading();
+		hupaController.showNotice("Your mail has been sent.", 10000);
+		History.back();
+	}
+
+<<<<<<< HEAD
+	public interface Displayable extends WidgetDisplayable {
+=======
+	public interface Displayable extends IsWidget {
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+		String getFromText();
+		void showCc();
+		void hideCc();
+		void showBcc();
+		void hideBcc();
+		void showReply();
+		void hideReply();
+		void showFollowup();
+		void hideFollowup();
+		HasText getTo();
+		HasText getCc();
+		HasText getBcc();
+		HasText getSubject();
+		HasClickHandlers getSendClick();
+		HasClickHandlers getCancelClick();
+		HasClickHandlers getCcClick();
+		HasClickHandlers get_CcClick();
+		HasClickHandlers getBccClick();
+		HasClickHandlers get_BccClick();
+		HasClickHandlers getReplyClick();
+		HasClickHandlers get_ReplyClick();
+		HasClickHandlers getFollowupClick();
+		HasClickHandlers get_FollowupClick();
+		boolean validate();
+		HasText getMessage();
+		HasHTML getMessageHTML();
+		ListBox getFromList();
+		IUploader getUploader();
+<<<<<<< HEAD
+=======
+		void fillContactList(String[] contacts);
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+	}
+}

Copied: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeToolBarActivity.java (from r1375909, james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/ContactsPresenterPlace.java)
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeToolBarActivity.java?p2=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeToolBarActivity.java&p1=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/ContactsPresenterPlace.java&r1=1375909&r2=1516164&rev=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/ContactsPresenterPlace.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ComposeToolBarActivity.java Wed Aug 21 14:08:19 2013
@@ -17,25 +17,32 @@
  * under the License.                                           *
  ****************************************************************/
 
-package org.apache.hupa.client.mvp.place;
+package org.apache.hupa.client.activity;
 
-import net.customware.gwt.presenter.client.gin.ProvidedPresenterPlace;
-
-import org.apache.hupa.client.mvp.ContactsPresenter;
+<<<<<<< HEAD
+import org.apache.hupa.client.ui.WidgetDisplayable;
 
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+=======
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+import com.google.gwt.user.client.ui.IsWidget;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
 import com.google.inject.Inject;
-import com.google.inject.Provider;
-
-public class ContactsPresenterPlace extends ProvidedPresenterPlace<ContactsPresenter>{
 
-    @Inject
-    public ContactsPresenterPlace(Provider<ContactsPresenter> presenter) {
-        super(presenter);
-    }
-
-    @Override
-    public String getName() {
-        return "Contacts";
-    }
+public class ComposeToolBarActivity extends AppBaseActivity {
 
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		container.setWidget(display.asWidget());
+	}
+
+	@Inject private Displayable display;
+	
+<<<<<<< HEAD
+	public interface Displayable extends WidgetDisplayable {}
+=======
+	public interface Displayable extends IsWidget {}
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
 }

Copied: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactPropertiesActivity.java (from r1375909, james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/ContactsPresenterPlace.java)
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactPropertiesActivity.java?p2=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactPropertiesActivity.java&p1=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/ContactsPresenterPlace.java&r1=1375909&r2=1516164&rev=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/ContactsPresenterPlace.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactPropertiesActivity.java Wed Aug 21 14:08:19 2013
@@ -17,25 +17,29 @@
  * under the License.                                           *
  ****************************************************************/
 
-package org.apache.hupa.client.mvp.place;
+package org.apache.hupa.client.activity;
 
-import net.customware.gwt.presenter.client.gin.ProvidedPresenterPlace;
+import java.util.List;
 
-import org.apache.hupa.client.mvp.ContactsPresenter;
+import org.apache.hupa.client.ui.LabelNode;
 
+import com.google.gwt.event.dom.client.HasClickHandlers;
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+import com.google.gwt.user.client.ui.IsWidget;
 import com.google.inject.Inject;
-import com.google.inject.Provider;
 
-public class ContactsPresenterPlace extends ProvidedPresenterPlace<ContactsPresenter>{
-
-    @Inject
-    public ContactsPresenterPlace(Provider<ContactsPresenter> presenter) {
-        super(presenter);
-    }
-
-    @Override
-    public String getName() {
-        return "Contacts";
-    }
+public class ContactPropertiesActivity extends AppBaseActivity {
 
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		container.setWidget(display.asWidget());
+	}
+
+	@Inject private Displayable display;
+
+	public interface Displayable extends IsWidget {
+		void cascade(LabelNode labelNode, List<LabelNode> list, int cascadeTypeAdd);
+		HasClickHandlers getSave();
+	}
 }

Added: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactsListActivity.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactsListActivity.java?rev=1516164&view=auto
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactsListActivity.java (added)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/ContactsListActivity.java Wed Aug 21 14:08:19 2013
@@ -0,0 +1,113 @@
+/****************************************************************
+ * 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.hupa.client.activity;
+
+import org.apache.hupa.client.HupaController;
+import org.apache.hupa.client.rf.DeleteFolderRequest;
+import org.apache.hupa.client.ui.LabelNode;
+import org.apache.hupa.shared.domain.DeleteFolderAction;
+import org.apache.hupa.shared.domain.GenericResult;
+import org.apache.hupa.shared.domain.ImapFolder;
+import org.apache.hupa.shared.events.DeleteFolderEvent;
+import org.apache.hupa.shared.events.DeleteFolderEventHandler;
+import org.apache.hupa.shared.events.RefreshLabelListEvent;
+import org.apache.hupa.shared.events.RefreshLabelListEventHandler;
+
+import com.google.gwt.event.dom.client.ClickEvent;
+import com.google.gwt.event.dom.client.ClickHandler;
+import com.google.gwt.event.dom.client.HasClickHandlers;
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.Window;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+import com.google.gwt.user.client.ui.IsWidget;
+import com.google.gwt.view.client.SingleSelectionModel;
+import com.google.inject.Inject;
+import com.google.web.bindery.requestfactory.shared.Receiver;
+import com.google.web.bindery.requestfactory.shared.ServerFailure;
+
+public class ContactsListActivity extends AppBaseActivity {
+
+	@Inject private HupaController hupaController;
+	@Inject private Displayable display;
+	@Inject private LabelPropertiesActivity.Displayable labelProperties;
+
+
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		container.setWidget(display.asWidget());
+		bindTo(eventBus);
+	}
+
+	private void bindTo(final EventBus eventBus) {
+		this.registerHandler(display.getDelete().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				if (Window.confirm("Are you sure?")) {
+					eventBus.fireEvent(new DeleteFolderEvent());
+				}
+			}
+		}));
+		eventBus.addHandler(DeleteFolderEvent.TYPE, new DeleteFolderEventHandler() {
+			@Override
+			public void onDeleteFolderEvent(DeleteFolderEvent event) {
+				deleteSelected();
+			}
+		});
+		eventBus.addHandler(RefreshLabelListEvent.TYPE, new RefreshLabelListEventHandler(){
+			@Override
+			public void onRefreshEvent(RefreshLabelListEvent event) {
+				display.refresh();
+			}
+		});
+	}
+
+	public interface Displayable extends IsWidget {
+		final int CASCADE_TYPE_ADD = 0x01;
+		final int CASCADE_TYPE_RENAME = 0x02;
+		SingleSelectionModel<LabelNode> getSelectionModel();
+		HasClickHandlers getAdd();
+		HasClickHandlers getDelete();
+		void refresh();
+	}
+
+	public void deleteSelected() {
+		hupaController.showTopLoading("Deleting...");
+		SingleSelectionModel<LabelNode> selectionModel = display.getSelectionModel();
+		LabelNode labelNode = selectionModel.getSelectedObject();
+		DeleteFolderRequest req = rf.deleteFolderRequest();
+		DeleteFolderAction action = req.create(DeleteFolderAction.class);
+		final ImapFolder f = req.create(ImapFolder.class);
+		f.setFullName(labelNode.getFolder().getFullName());
+		action.setFolder(f);
+		req.delete(action).fire(new Receiver<GenericResult>() {
+			@Override
+			public void onSuccess(GenericResult response) {
+				hupaController.hideTopLoading();
+				display.refresh();
+				hupaController.showNotice("The label \"" + f.getFullName() + "\" was deleted.", 10000);
+			}
+			@Override
+			public void onFailure(ServerFailure error) {
+				hupaController.hideTopLoading();
+				hupaController.showNotice(error.getMessage(), 10000);
+			}
+		});
+	}
+}

Copied: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/FolderListActivity.java (from r1375909, james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/HupaPlaceManager.java)
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/FolderListActivity.java?p2=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/FolderListActivity.java&p1=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/HupaPlaceManager.java&r1=1375909&r2=1516164&rev=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/HupaPlaceManager.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/FolderListActivity.java Wed Aug 21 14:08:19 2013
@@ -17,23 +17,50 @@
  * under the License.                                           *
  ****************************************************************/
 
-package org.apache.hupa.client.mvp.place;
+package org.apache.hupa.client.activity;
 
-import net.customware.gwt.presenter.client.EventBus;
-import net.customware.gwt.presenter.client.place.DefaultPlaceManager;
-import net.customware.gwt.presenter.client.place.TokenFormatter;
+<<<<<<< HEAD
+import org.apache.hupa.client.ui.WidgetDisplayable;
 
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+=======
+import org.apache.hupa.shared.events.RefreshUnreadEvent;
+import org.apache.hupa.shared.events.RefreshUnreadEventHandler;
+
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+import com.google.gwt.user.client.ui.IsWidget;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
 import com.google.inject.Inject;
 
-/**
- * PlaceManager implementation for Hupa
- * 
- *
- */
-public class HupaPlaceManager extends DefaultPlaceManager{
-    @Inject
-    public HupaPlaceManager(EventBus eventBus, TokenFormatter tokenFormatter, LoginPresenterPlace loginPresenterPlace, IMAPMessageListPresenterPlace messageListPresenterPlace, IMAPMessagePresenterPlace imapMessagePresenterPlace, MessageSendPresenterPlace sendPresenterPlace, ContactsPresenterPlace contactsPresenterPlace) {
-        super(eventBus, tokenFormatter, loginPresenterPlace, messageListPresenterPlace, imapMessagePresenterPlace, sendPresenterPlace, contactsPresenterPlace);
-    }
+public class FolderListActivity extends AppBaseActivity {
+
+	@Inject private Displayable display;
+
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		container.setWidget(display.asWidget());
+<<<<<<< HEAD
+	}
+
+	public interface Displayable extends WidgetDisplayable {
+=======
+		bindTo(eventBus);
+	}
+
+	private void bindTo(EventBus eventBus) {
+
+		eventBus.addHandler(RefreshUnreadEvent.TYPE, new RefreshUnreadEventHandler() {
+			@Override
+			public void onRefreshEvent(RefreshUnreadEvent event) {
+				display.refresh();
+			}
+		});
+	}
 
+	public interface Displayable extends IsWidget {
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+		void refresh();
+	}
 }

Added: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/IMAPMessageListActivity.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/IMAPMessageListActivity.java?rev=1516164&view=auto
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/IMAPMessageListActivity.java (added)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/IMAPMessageListActivity.java Wed Aug 21 14:08:19 2013
@@ -0,0 +1,375 @@
+/****************************************************************
+ * 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.hupa.client.activity;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Set;
+
+import org.apache.hupa.client.activity.MessageSendActivity.Type;
+import org.apache.hupa.client.place.FolderPlace;
+import org.apache.hupa.client.place.MessageSendPlace;
+import org.apache.hupa.client.rf.DeleteMessageAllRequest;
+import org.apache.hupa.client.rf.DeleteMessageByUidRequest;
+import org.apache.hupa.client.rf.MoveMessageRequest;
+import org.apache.hupa.client.rf.SetFlagRequest;
+import org.apache.hupa.client.ui.MessagesCellTable;
+import org.apache.hupa.client.ui.WidgetDisplayable;
+import org.apache.hupa.client.widgets.HasDialog;
+import org.apache.hupa.shared.data.MessageImpl.IMAPFlag;
+import org.apache.hupa.shared.domain.DeleteMessageAllAction;
+import org.apache.hupa.shared.domain.DeleteMessageByUidAction;
+import org.apache.hupa.shared.domain.DeleteMessageResult;
+import org.apache.hupa.shared.domain.GenericResult;
+import org.apache.hupa.shared.domain.ImapFolder;
+import org.apache.hupa.shared.domain.Message;
+import org.apache.hupa.shared.domain.MoveMessageAction;
+import org.apache.hupa.shared.domain.SetFlagAction;
+import org.apache.hupa.shared.domain.User;
+import org.apache.hupa.shared.events.DecreaseUnseenEvent;
+import org.apache.hupa.shared.events.FolderSelectionEvent;
+import org.apache.hupa.shared.events.FolderSelectionEventHandler;
+import org.apache.hupa.shared.events.IncreaseUnseenEvent;
+import org.apache.hupa.shared.events.LoadMessagesEvent;
+import org.apache.hupa.shared.events.LogoutEvent;
+import org.apache.hupa.shared.events.LogoutEventHandler;
+import org.apache.hupa.shared.events.MessagesReceivedEvent;
+import org.apache.hupa.shared.events.MessagesReceivedEventHandler;
+import org.apache.hupa.shared.events.MoveMessageEvent;
+import org.apache.hupa.shared.events.MoveMessageEventHandler;
+import org.apache.hupa.widgets.ui.HasEnable;
+
+import com.google.gwt.event.dom.client.ChangeEvent;
+import com.google.gwt.event.dom.client.ChangeHandler;
+import com.google.gwt.event.dom.client.ClickEvent;
+import com.google.gwt.event.dom.client.ClickHandler;
+import com.google.gwt.event.dom.client.HasChangeHandlers;
+import com.google.gwt.event.dom.client.HasClickHandlers;
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+import com.google.gwt.user.client.ui.HasValue;
+import com.google.inject.Inject;
+import com.google.inject.Provider;
+import com.google.web.bindery.requestfactory.shared.Receiver;
+
+public class IMAPMessageListActivity extends AppBaseActivity {
+
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		bind();
+		revealDisplay(user, folder, searchValue);
+		container.setWidget(display.asWidget());
+	}
+	private void bind() {
+		eventBus.addHandler(LogoutEvent.TYPE, new LogoutEventHandler() {
+			public void onLogout(LogoutEvent logoutEvent) {
+				IMAPMessageListActivity.this.display.reset();
+				IMAPMessageListActivity.this.display.getSearchValue().setValue("");
+			}
+		});
+		eventBus.addHandler(MessagesReceivedEvent.TYPE, new MessagesReceivedEventHandler() {
+			public void onMessagesReceived(MessagesReceivedEvent event) {
+				// fill the oracle
+				display.fillSearchOracle(event.getMessages());
+			}
+		});
+		registrations.add(display.getSearchClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				String searchValue = null;
+				if (display.getSearchValue().getValue().trim().length() > 0) {
+					searchValue = display.getSearchValue().getValue().trim();
+				}
+				eventBus.fireEvent(new LoadMessagesEvent(user, folder, searchValue));
+			}
+		}));
+		eventBus.addHandler(MoveMessageEvent.TYPE, new MoveMessageEventHandler() {
+			public void onMoveMessageHandler(MoveMessageEvent event) {
+				final Message message = event.getMessage();
+				MoveMessageRequest req = rf.moveMessageRequest();
+				MoveMessageAction action = req.create(MoveMessageAction.class);
+				ImapFolder newOne = req.create(ImapFolder.class);
+				ImapFolder oldOne = req.create(ImapFolder.class);
+				event.getNewFolder().setFolderTo(newOne);
+				event.getOldFolder().setFolderTo(oldOne);
+				action.setMessageUid(message.getUid());
+				action.setNewFolder(newOne);
+				action.setOldFolder(oldOne);
+				req.move(action).fire(new Receiver<GenericResult>() {
+					@Override
+					public void onSuccess(GenericResult response) {
+						List<Message> messageArray = new ArrayList<Message>();
+						messageArray.add(message);
+						display.removeMessages(messageArray);
+					}
+				});
+			}
+		});
+		registrations.add(display.getSelectAllClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				display.deselectAllMessages();
+				display.selectAllMessages();
+			}
+		}));
+		registrations.add(display.getSelectNoneClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				display.deselectAllMessages();
+			}
+		}));
+		registrations.add(display.getDeleteClick().addClickHandler(new com.google.gwt.event.dom.client.ClickHandler() {
+			public void onClick(com.google.gwt.event.dom.client.ClickEvent event) {
+				if (folder.getFullName().equals(user.getSettings().getTrashFolderName())) {
+					display.getConfirmDeleteDialog().show();
+				} else {
+					deleteMessages();
+				}
+			}
+		}));
+		registrations.add(display.getConfirmDeleteDialogClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				deleteMessages();
+			}
+		}));
+		registrations.add(display.getNewClick().addClickHandler(new com.google.gwt.event.dom.client.ClickHandler() {
+			public void onClick(com.google.gwt.event.dom.client.ClickEvent event) {
+				// eventBus.fireEvent(new NewMessageEvent());
+				pc.goTo(messageSendPlaceProvider.get().with(user, null, null, null, Type.NEW));
+			}
+		}));
+		registrations.add(display.getDeleteAllClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				display.getConfirmDeleteAllDialog().center();
+			}
+		}));
+		registrations.add(display.getConfirmDeleteAllDialogClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				DeleteMessageAllRequest req = rf.deleteMessageAllRequest();
+				DeleteMessageAllAction action = req.create(DeleteMessageAllAction.class);
+				ImapFolder f = req.create(ImapFolder.class);
+				folder.setFolderTo(f);
+				action.setFolder(f);
+				req.delete(action).fire(new Receiver<DeleteMessageResult>() {
+					@Override
+					public void onSuccess(DeleteMessageResult response) {
+						redrawTable();
+						eventBus.fireEvent(new DecreaseUnseenEvent(user, folder, response.getCount()));
+					}
+				});
+			}
+		}));
+		registrations.add(display.getMarkSeenClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				final ArrayList<Message> selectedMessages = new ArrayList<Message>(display.getSelectedMessages());
+				ArrayList<Long> uids = new ArrayList<Long>();
+				for (Message m : selectedMessages) {
+					if (m.getFlags().contains(IMAPFlag.SEEN) == false) {
+						uids.add(m.getUid());
+					} else {
+						selectedMessages.remove(m);
+					}
+				}
+				SetFlagRequest req = rf.setFlagRequest();
+				SetFlagAction action = req.create(SetFlagAction.class);
+				ImapFolder f = req.create(ImapFolder.class);
+				folder.setFolderTo(f);
+				action.setFlag(IMAPFlag.SEEN);
+				action.setFolder(f);
+				action.setUids(uids);
+				action.setValue(true);
+				req.set(action).fire(new Receiver<GenericResult>() {
+					@Override
+					public void onSuccess(GenericResult response) {
+						for (Message m : selectedMessages) {
+							if (m.getFlags().contains(IMAPFlag.SEEN) == false) {
+								m.getFlags().add(IMAPFlag.SEEN);
+							}
+						}
+						display.redraw();
+						eventBus.fireEvent(new DecreaseUnseenEvent(user, folder, selectedMessages.size()));
+					}
+				});
+			}
+		}));
+		registrations.add(display.getMarkUnseenClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				final ArrayList<Message> selectedMessages = new ArrayList<Message>(display.getSelectedMessages());
+				ArrayList<Long> uids = new ArrayList<Long>();
+				for (Message m : selectedMessages) {
+					if (m.getFlags().contains(IMAPFlag.SEEN)) {
+						uids.add(m.getUid());
+					} else {
+						selectedMessages.remove(m);
+					}
+				}
+				SetFlagRequest req = rf.setFlagRequest();
+				SetFlagAction action = req.create(SetFlagAction.class);
+				ImapFolder f = req.create(ImapFolder.class);
+				folder.setFolderTo(f);
+				action.setFlag(IMAPFlag.SEEN);
+				action.setFolder(f);
+				action.setUids(uids);
+				action.setValue(false);
+				req.set(action).fire(new Receiver<GenericResult>() {
+					@Override
+					public void onSuccess(GenericResult response) {
+						for (Message m : selectedMessages) {
+							if (m.getFlags().contains(IMAPFlag.SEEN)) {
+								m.getFlags().remove(IMAPFlag.SEEN);
+							}
+						}
+						display.redraw();
+						eventBus.fireEvent(new IncreaseUnseenEvent(user, folder, selectedMessages.size()));
+					}
+				});
+			}
+
+		}));
+		eventBus.addHandler(FolderSelectionEvent.TYPE, new FolderSelectionEventHandler() {// TODO
+			        public void onFolderSelectionEvent(FolderSelectionEvent event) {
+				        folder = event.getFolder();
+				        user = event.getUser();
+			        }
+
+		        });
+		registrations.add(display.getRefreshClick().addClickHandler(new ClickHandler() {
+			public void onClick(ClickEvent event) {
+				display.reset();
+				display.reloadData();
+			}
+
+		}));
+		registrations.add(display.getRowsPerPageChange().addChangeHandler(new ChangeHandler() {
+			public void onChange(ChangeEvent event) {
+				// firePresenterRevealedEvent(true);
+				// firePresenterChangedEvent();
+			}
+
+		}));
+		// display.addTableListener(tableListener);
+	}
+
+	private void deleteMessages() {
+		Set<Message> ml = display.getSelectedMessages();
+		final List<Message> selectedMessages = new ArrayList<Message>(ml);
+		List<Long> uids = new ArrayList<Long>();
+		for (Message m : selectedMessages) {
+			uids.add(m.getUid());
+			display.getTable().getSelectionModel().setSelected(m, false); // FIXME should be deSelected, or removed?
+		}
+		// maybe its better to just remove the messages from the table and
+		// expect the removal will work
+		display.removeMessages(selectedMessages);
+		DeleteMessageByUidRequest req = rf.deleteMessageByUidRequest();
+		DeleteMessageByUidAction action = req.create(DeleteMessageByUidAction.class);
+		ImapFolder f = req.create(ImapFolder.class);
+//		folder.setFolderTo(f); FIXME cannot use any more, for it's already a requestContext assigned.
+		clone(f, folder);
+		action.setMessageUids(uids);
+		action.setFolder(f);
+		req.delete(action).fire(new Receiver<DeleteMessageResult>() {
+			@Override
+			public void onSuccess(DeleteMessageResult response) {
+				redrawTable();//TODO presenter
+				eventBus.fireEvent(new DecreaseUnseenEvent(user, folder, response.getCount()));
+			}
+		});
+	}
+	private void clone(ImapFolder f, ImapFolder folder) {
+	    f.setChildren(folder.getChildren());
+		f.setDelimiter(folder.getDelimiter());
+		f.setFullName(folder.getFullName());
+		f.setMessageCount(folder.getMessageCount());
+		f.setName(folder.getName());
+		f.setSubscribed(folder.getSubscribed());
+		f.setUnseenMessageCount(folder.getUnseenMessageCount());
+    }
+
+	private void redrawTable() {
+        display.getTable().setVisibleRangeAndClearData(display.getTable().getVisibleRange(), true);
+    }
+	public IMAPMessageListActivity with(FolderPlace place) {
+//		this.user = place.getUser();
+//		this.folder = place.getFolder();
+//		this.searchValue = place.getSearchValue();
+		return this;
+	}
+
+	protected void onRevealDisplay() {
+		if (user != null && folder != null) {
+			display.reloadData();
+		}
+	}
+	public void revealDisplay(User user, ImapFolder folder, String searchValue) {
+		this.user = user;
+		if (this.user == null || !this.user.getName().equals(user.getName()) || this.folder == null
+		        || !this.folder.getFullName().equals(folder.getFullName())
+		        || (searchValue == null && this.searchValue != null)
+		        || (searchValue != null && searchValue.equals(this.searchValue) == false)) {
+			display.reset();
+			display.deselectAllMessages();
+		}
+		display.setExpandLoading(false);
+		this.searchValue = searchValue;
+		this.folder = folder;
+		onRevealDisplay();
+	}
+
+	private String searchValue;
+	private User user;
+	private ImapFolder folder;
+
+	@Inject private Displayable display;
+	@Inject private Provider<MessageSendPlace> messageSendPlaceProvider;
+	
+	public interface Displayable extends WidgetDisplayable {
+		public void setPostFetchMessageCount(int count);
+		public void fillSearchOracle(List<Message> messages);
+		public void setExpandLoading(boolean expanding);
+		public void redraw();
+		public void goToPage(int page);
+		public void reloadData();
+		public void removeMessages(List<Message> messages);
+		public void selectAllMessages();
+		public void deselectAllMessages();
+		public void reset();
+		public int getCurrentPage();
+		public int getRowsPerPageIndex();
+		public HasClickHandlers getNewClick();
+		public Message getData(int rowIndex);
+		public HasClickHandlers getDeleteClick();
+		public HasClickHandlers getDeleteAllClick();
+		public HasEnable getDeleteEnable();
+		public Set<Message> getSelectedMessages();
+		public HasDialog getConfirmDeleteDialog();
+		public HasDialog getConfirmDeleteAllDialog();
+		public HasClickHandlers getConfirmDeleteDialogClick();
+		public HasClickHandlers getConfirmDeleteAllDialogClick();
+		public HasClickHandlers getSelectAllClick();
+		public HasClickHandlers getSelectNoneClick();
+		public HasClickHandlers getMarkSeenClick();
+		public HasClickHandlers getMarkUnseenClick();
+		public HasEnable getMarkSeenEnable();
+		public HasEnable getMarkUnseenEnable();
+		public HasClickHandlers getRefreshClick();
+		public HasChangeHandlers getRowsPerPageChange();
+		public HasClickHandlers getSearchClick();
+		public HasValue<String> getSearchValue();
+		public MessagesCellTable getTable();
+	}
+}

Added: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelListActivity.java
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelListActivity.java?rev=1516164&view=auto
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelListActivity.java (added)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelListActivity.java Wed Aug 21 14:08:19 2013
@@ -0,0 +1,124 @@
+/****************************************************************
+ * 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.hupa.client.activity;
+
+import org.apache.hupa.client.HupaController;
+import org.apache.hupa.client.rf.DeleteFolderRequest;
+import org.apache.hupa.client.ui.LabelNode;
+<<<<<<< HEAD
+import org.apache.hupa.client.ui.WidgetDisplayable;
+=======
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+import org.apache.hupa.shared.domain.DeleteFolderAction;
+import org.apache.hupa.shared.domain.GenericResult;
+import org.apache.hupa.shared.domain.ImapFolder;
+import org.apache.hupa.shared.events.DeleteFolderEvent;
+import org.apache.hupa.shared.events.DeleteFolderEventHandler;
+import org.apache.hupa.shared.events.RefreshLabelListEvent;
+import org.apache.hupa.shared.events.RefreshLabelListEventHandler;
+
+import com.google.gwt.event.dom.client.ClickEvent;
+import com.google.gwt.event.dom.client.ClickHandler;
+import com.google.gwt.event.dom.client.HasClickHandlers;
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.Window;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+<<<<<<< HEAD
+=======
+import com.google.gwt.user.client.ui.IsWidget;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+import com.google.gwt.view.client.SingleSelectionModel;
+import com.google.inject.Inject;
+import com.google.web.bindery.requestfactory.shared.Receiver;
+import com.google.web.bindery.requestfactory.shared.ServerFailure;
+
+public class LabelListActivity extends AppBaseActivity {
+
+	@Inject private HupaController hupaController;
+	@Inject private Displayable display;
+	@Inject private LabelPropertiesActivity.Displayable labelProperties;
+
+
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		container.setWidget(display.asWidget());
+		bindTo(eventBus);
+	}
+
+	private void bindTo(final EventBus eventBus) {
+		this.registerHandler(display.getDelete().addClickHandler(new ClickHandler() {
+			@Override
+			public void onClick(ClickEvent event) {
+				if (Window.confirm("Are you sure?")) {
+					eventBus.fireEvent(new DeleteFolderEvent());
+				}
+			}
+		}));
+		eventBus.addHandler(DeleteFolderEvent.TYPE, new DeleteFolderEventHandler() {
+			@Override
+			public void onDeleteFolderEvent(DeleteFolderEvent event) {
+				deleteSelected();
+			}
+		});
+		eventBus.addHandler(RefreshLabelListEvent.TYPE, new RefreshLabelListEventHandler(){
+			@Override
+			public void onRefreshEvent(RefreshLabelListEvent event) {
+				display.refresh();
+			}
+		});
+	}
+
+<<<<<<< HEAD
+	public interface Displayable extends WidgetDisplayable {
+=======
+	public interface Displayable extends IsWidget {
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+		final int CASCADE_TYPE_ADD = 0x01;
+		final int CASCADE_TYPE_RENAME = 0x02;
+		SingleSelectionModel<LabelNode> getSelectionModel();
+		HasClickHandlers getAdd();
+		HasClickHandlers getDelete();
+		void refresh();
+	}
+
+	public void deleteSelected() {
+		hupaController.showTopLoading("Deleting...");
+		SingleSelectionModel<LabelNode> selectionModel = display.getSelectionModel();
+		LabelNode labelNode = selectionModel.getSelectedObject();
+		DeleteFolderRequest req = rf.deleteFolderRequest();
+		DeleteFolderAction action = req.create(DeleteFolderAction.class);
+		final ImapFolder f = req.create(ImapFolder.class);
+		f.setFullName(labelNode.getFolder().getFullName());
+		action.setFolder(f);
+		req.delete(action).fire(new Receiver<GenericResult>() {
+			@Override
+			public void onSuccess(GenericResult response) {
+				hupaController.hideTopLoading();
+				display.refresh();
+				hupaController.showNotice("The label \"" + f.getFullName() + "\" was deleted.", 10000);
+			}
+			@Override
+			public void onFailure(ServerFailure error) {
+				hupaController.hideTopLoading();
+				hupaController.showNotice(error.getMessage(), 10000);
+			}
+		});
+	}
+}

Copied: james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelPropertiesActivity.java (from r1375909, james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/HupaPlaceManager.java)
URL: http://svn.apache.org/viewvc/james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelPropertiesActivity.java?p2=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelPropertiesActivity.java&p1=james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/HupaPlaceManager.java&r1=1375909&r2=1516164&rev=1516164&view=diff
==============================================================================
--- james/hupa/trunk/client/src/main/java/org/apache/hupa/client/mvp/place/HupaPlaceManager.java (original)
+++ james/hupa/trunk/client/src/main/java/org/apache/hupa/client/activity/LabelPropertiesActivity.java Wed Aug 21 14:08:19 2013
@@ -17,23 +17,40 @@
  * under the License.                                           *
  ****************************************************************/
 
-package org.apache.hupa.client.mvp.place;
+package org.apache.hupa.client.activity;
 
-import net.customware.gwt.presenter.client.EventBus;
-import net.customware.gwt.presenter.client.place.DefaultPlaceManager;
-import net.customware.gwt.presenter.client.place.TokenFormatter;
+import java.util.List;
 
+import org.apache.hupa.client.ui.LabelNode;
+<<<<<<< HEAD
+import org.apache.hupa.client.ui.WidgetDisplayable;
+=======
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+
+import com.google.gwt.event.dom.client.HasClickHandlers;
+import com.google.gwt.event.shared.EventBus;
+import com.google.gwt.user.client.ui.AcceptsOneWidget;
+<<<<<<< HEAD
+=======
+import com.google.gwt.user.client.ui.IsWidget;
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
 import com.google.inject.Inject;
 
-/**
- * PlaceManager implementation for Hupa
- * 
- *
- */
-public class HupaPlaceManager extends DefaultPlaceManager{
-    @Inject
-    public HupaPlaceManager(EventBus eventBus, TokenFormatter tokenFormatter, LoginPresenterPlace loginPresenterPlace, IMAPMessageListPresenterPlace messageListPresenterPlace, IMAPMessagePresenterPlace imapMessagePresenterPlace, MessageSendPresenterPlace sendPresenterPlace, ContactsPresenterPlace contactsPresenterPlace) {
-        super(eventBus, tokenFormatter, loginPresenterPlace, messageListPresenterPlace, imapMessagePresenterPlace, sendPresenterPlace, contactsPresenterPlace);
-    }
+public class LabelPropertiesActivity extends AppBaseActivity {
+
+	@Override
+	public void start(AcceptsOneWidget container, EventBus eventBus) {
+		container.setWidget(display.asWidget());
+	}
+
+	@Inject private Displayable display;
 
+<<<<<<< HEAD
+	public interface Displayable extends WidgetDisplayable {
+=======
+	public interface Displayable extends IsWidget {
+>>>>>>> 7635f4a0e76a4bbbeb6a4029aff92087f00eb09f
+		void cascade(LabelNode labelNode, List<LabelNode> list, int cascadeTypeAdd);
+		HasClickHandlers getSave();
+	}
 }



---------------------------------------------------------------------
To unsubscribe, e-mail: server-dev-unsubscribe@james.apache.org
For additional commands, e-mail: server-dev-help@james.apache.org