You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ambari.apache.org by ma...@apache.org on 2012/10/08 03:38:08 UTC

svn commit: r1395430 [10/13] - in /incubator/ambari/branches/AMBARI-666: ./ ambari-agent/src/main/puppet/manifestloader/ ambari-agent/src/main/puppet/modules/configgenerator/manifests/ ambari-agent/src/main/puppet/modules/hdp-hadoop/manifests/ ambari-a...

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/ResourceProvider.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/ResourceProvider.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/ResourceProvider.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/ResourceProvider.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,116 @@
+/**
+ * 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.ambari.server.controller.spi;
+
+import org.apache.ambari.server.AmbariException;
+
+import java.util.List;
+import java.util.Set;
+
+/**
+ * The resource provider allows for the plugging in of a back end data store
+ * for a resource type.  The resource provider is associated with a specific
+ * resource type and can be queried for a list of resources of that type.
+ * The resource provider plugs into and is used by the
+ * {@link ClusterController cluster controller} to obtain a list of resources
+ * for a given request.
+ */
+public interface ResourceProvider {
+
+  /**
+   * Create the resources defined by the properties in the given request object.
+   *
+   * @param request  the request object which defines the set of properties
+   *                 for the resources to be created
+   *
+   * @throws AmbariException thrown if the resources cannot be created
+   */
+  public void createResources(Request request) throws AmbariException;
+
+  /**
+   * Get a set of {@link Resource resources} based on the given request and predicate
+   * information.
+   * </p>
+   * Note that it is not required for this resource provider to completely filter
+   * the set of resources based on the given predicate.  It may not be possible
+   * since some of the properties involved may be provided by another
+   * {@link PropertyProvider provider}.  This partial filtering is allowed because
+   * the predicate will always be applied by the calling cluster controller.  The
+   * predicate is made available at this level so that some pre-filtering can be done
+   * as an optimization.
+   * </p>
+   * A simple implementation of a resource provider may choose to just return all of
+   * the resources of a given type and allow the calling cluster controller to filter
+   * based on the predicate.
+   *
+   * @param request    the request object which defines the desired set of properties
+   * @param predicate  the predicate object which can be used to filter which
+   *                   resources are returned
+   * @return a set of resources based on the given request and predicate information
+   *
+   * @throws AmbariException thrown if the resources cannot be obtained
+   */
+  public Set<Resource> getResources(Request request, Predicate predicate) throws AmbariException;
+
+  /**
+   * Update the resources selected by the given predicate with the properties
+   * from the given request object.
+   *
+   * @param request    the request object which defines the set of properties
+   *                   for the resources to be updated
+   * @param predicate  the predicate object which can be used to filter which
+   *                   resources are updated
+   *
+   * @throws AmbariException thrown if the resource cannot be updated
+   */
+  public void updateResources(Request request, Predicate predicate) throws AmbariException;
+
+  /**
+   * Delete the resources selected by the given predicate.
+   *
+   * @param predicate the predicate object which can be used to filter which
+   *                  resources are deleted
+   *
+   * @throws AmbariException thrown if the resource cannot be deleted
+   */
+  public void deleteResources(Predicate predicate) throws AmbariException;
+
+  /**
+   * Get the set of property ids for the properties that this provider can provide.
+   *
+   * @return the set of property ids for the properties that this provider can provide
+   */
+  public Set<PropertyId> getPropertyIds();
+
+  /**
+   * Get the list of property providers for the resource associated with this provider's
+   * resource type.
+   *
+   * @return the list of property providers
+   */
+  public List<PropertyProvider> getPropertyProviders();
+
+  /**
+   * Get the {@link Schema schema} for this provider's resource type.  The schema
+   * for a given resource type describes the properties and categories provided
+   * by that type of resource.
+   *
+   * @return the schema object
+   */
+  public Schema getSchema();
+}

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/Schema.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/Schema.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/Schema.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/controller/spi/Schema.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,53 @@
+/**
+ * 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.ambari.server.controller.spi;
+
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * The schema is used to describe all of the properties that a resource type
+ * supports.
+ */
+public interface Schema {
+
+  /**
+   * Get the property id for the property that uniquely identifies
+   * the given resource type for the resource described by this schema.
+   * </p>
+   * For example, the resource 'HostComponent' is uniquely identified by
+   * its associated 'Cluster', 'Host' and 'Component' resources.  Passing
+   * the 'Host' resource type to
+   * {@link Schema#getKeyPropertyId(org.apache.ambari.server.controller.spi.Resource.Type)}
+   * on a schema object of a 'HostComponent' resource will return the id of the
+   * property of the foreign key reference from the 'HostComponent' to the 'Host'.
+   *
+   * @param type the resource type
+   * @return the key property id for the given resource type
+   */
+  public PropertyId getKeyPropertyId(Resource.Type type);
+
+  /**
+   * Get the map of categories for this schema's resource.  The map
+   * is keyed by the category name and contains sets of property ids
+   * for each category.
+   *
+   * @return the map of categories
+   */
+  public Map<String, Set<String>> getCategories();
+}

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/RoleDAO.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/RoleDAO.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/RoleDAO.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/RoleDAO.java Mon Oct  8 01:37:59 2012
@@ -34,18 +34,18 @@ public class RoleDAO {
   }
 
   @Transactional
-  public void create(RoleEntity roleName) {
-    entityManagerProvider.get().persist(roleName);
+  public void create(RoleEntity role) {
+    entityManagerProvider.get().persist(role);
   }
 
   @Transactional
-  public RoleEntity merge(RoleEntity roleName) {
-    return entityManagerProvider.get().merge(roleName);
+  public RoleEntity merge(RoleEntity role) {
+    return entityManagerProvider.get().merge(role);
   }
 
   @Transactional
-  public void remove(RoleEntity roleName) {
-    entityManagerProvider.get().remove(roleName);
+  public void remove(RoleEntity role) {
+    entityManagerProvider.get().remove(role);
   }
 
   @Transactional

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/UserDAO.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/UserDAO.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/UserDAO.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/dao/UserDAO.java Mon Oct  8 01:37:59 2012
@@ -34,13 +34,14 @@ public class UserDAO {
 
   @Transactional
   public UserEntity findByPK(UserEntityPK userPK) {
+    userPK.setUserName(userPK.getUserName().toLowerCase());
     return entityManagerProvider.get().find(UserEntity.class, userPK);
   }
 
   @Transactional
   public UserEntity findLocalUserByName(String userName) {
     TypedQuery<UserEntity> query = entityManagerProvider.get().createNamedQuery("localUserByName", UserEntity.class);
-    query.setParameter("username", userName);
+    query.setParameter("username", userName.toLowerCase());
     try {
       return query.getSingleResult();
     } catch (NoResultException e) {
@@ -50,7 +51,7 @@ public class UserDAO {
 
   public UserEntity findLdapUserByName(String userName) {
     TypedQuery<UserEntity> query = entityManagerProvider.get().createNamedQuery("ldapUserByName", UserEntity.class);
-    query.setParameter("username", userName);
+    query.setParameter("username", userName.toLowerCase());
     try {
       return query.getSingleResult();
     } catch (NoResultException e) {
@@ -59,13 +60,15 @@ public class UserDAO {
   }
 
   @Transactional
-  public void create(UserEntity userName) {
-    entityManagerProvider.get().persist(userName);
+  public void create(UserEntity user) {
+    user.setUserName(user.getUserName().toLowerCase());
+    entityManagerProvider.get().persist(user);
   }
 
   @Transactional
-  public UserEntity merge(UserEntity userName) {
-    return entityManagerProvider.get().merge(userName);
+  public UserEntity merge(UserEntity user) {
+    user.setUserName(user.getUserName().toLowerCase());
+    return entityManagerProvider.get().merge(user);
   }
 
   @Transactional

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/entities/UserEntity.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/entities/UserEntity.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/entities/UserEntity.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/orm/entities/UserEntity.java Mon Oct  8 01:37:59 2012
@@ -27,8 +27,8 @@ import java.util.Set;
 @javax.persistence.Table(name = "users", schema = "ambari", catalog = "")
 @Entity
 @NamedQueries({
-        @NamedQuery(name = "localUserByName", query = "SELECT user FROM UserEntity user where user.userName=:username AND user.ldapUser=false"),
-        @NamedQuery(name = "ldapUserByName", query = "SELECT user FROM UserEntity user where user.userName=:username AND user.ldapUser=true")
+        @NamedQuery(name = "localUserByName", query = "SELECT user FROM UserEntity user where lower(user.userName)=:username AND user.ldapUser=false"),
+        @NamedQuery(name = "ldapUserByName", query = "SELECT user FROM UserEntity user where lower(user.userName)=:username AND user.ldapUser=true")
 })
 public class UserEntity {
 

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Cluster.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Cluster.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Cluster.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Cluster.java Mon Oct  8 01:37:59 2012
@@ -22,6 +22,7 @@ import java.util.List;
 import java.util.Map;
 
 import org.apache.ambari.server.AmbariException;
+import org.apache.ambari.server.controller.ClusterResponse;
 
 public interface Cluster {
 
@@ -66,4 +67,24 @@ public interface Cluster {
    */
   public List<ServiceComponentHost> getServiceComponentHosts(String hostname);
 
+  /**
+   * Get Stack Version
+   * @return
+   */
+  public StackVersion getDesiredStackVersion();
+
+  /**
+   * Set stack version
+   * @param stackVersion
+   */
+  public void setDesiredStackVersion(StackVersion stackVersion);
+
+  public Map<String, Config> getConfigsByType(String configType);
+
+  public Config getConfig(String configType, String versionTag);
+
+  public void addConfig(Config config);
+
+  public ClusterResponse convertToResponse();
+
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Clusters.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Clusters.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Clusters.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Clusters.java Mon Oct  8 01:37:59 2012
@@ -19,6 +19,8 @@
 package org.apache.ambari.server.state;
 
 import java.util.List;
+import java.util.Map;
+import java.util.Set;
 
 import org.apache.ambari.server.AmbariException;
 
@@ -42,10 +44,16 @@ public interface Clusters {
   public Cluster getCluster(String clusterName) throws AmbariException;
 
   /**
+   * Get all known clusters
+   * @return
+   */
+  public Map<String, Cluster> getClusters();
+
+  /**
    * Get all hosts being tracked by the Ambari server
    * @return
    */
-  public List<Host> getAllHosts();
+  public List<Host> getHosts();
 
   /**
    * Returns all the cluster names for this hostname.
@@ -53,9 +61,10 @@ public interface Clusters {
    * @return List of cluster names
    * @throws AmbariException
    */
-  public List<Cluster> getClustersForHost(String hostname)
+  public Set<Cluster> getClustersForHost(String hostname)
       throws AmbariException;
 
+
   /**
    * Get a Host object managed by this server
    * @param hostname Name of the host requested
@@ -81,8 +90,8 @@ public interface Clusters {
   public void mapHostToCluster(String hostname, String clusterName)
       throws AmbariException;
 
-  // TODO for Jitendra to fix in Heartbeat Handler as this function
-  // will not be supported
-  public List<String> getHostComponents(String hostname);
+
+  public void mapHostsToCluster(List<String> hostnames, String clusterName)
+      throws AmbariException;
 
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ConfigImpl.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ConfigImpl.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ConfigImpl.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ConfigImpl.java Mon Oct  8 01:37:59 2012
@@ -24,11 +24,11 @@ import java.util.List;
 import java.util.Map;
 
 public class ConfigImpl implements Config {
-  
+
   private final String type;
-  
+
   private String versionTag;
-  
+
   private Map<String, String> properties;
 
   public ConfigImpl(String type, String versionTag,
@@ -37,11 +37,11 @@ public class ConfigImpl implements Confi
     this.versionTag = versionTag;
     this.properties = properties;
   }
-  
+
   public ConfigImpl(String type, String versionTag) {
     this(type, versionTag, new HashMap<String, String>());
   }
-  
+
   @Override
   public String getType() {
     return type;
@@ -78,7 +78,7 @@ public class ConfigImpl implements Confi
       this.properties.remove(key);
     }
   }
-  
-  
+
+
 
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Host.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Host.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Host.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Host.java Mon Oct  8 01:37:59 2012
@@ -22,8 +22,9 @@ import java.util.List;
 import java.util.Map;
 
 import org.apache.ambari.server.agent.DiskInfo;
+import org.apache.ambari.server.controller.HostResponse;
 import org.apache.ambari.server.state.fsm.InvalidStateTransitonException;
-import org.apache.ambari.server.state.live.job.Job;
+import org.apache.ambari.server.state.job.Job;
 
 public interface Host {
 
@@ -241,4 +242,7 @@ public interface Host {
    * @return Time spent in current state.
    */
   public long getTimeInState();
+
+  public HostResponse convertToResponse();
+
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Service.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Service.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Service.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/Service.java Mon Oct  8 01:37:59 2012
@@ -20,32 +20,50 @@ package org.apache.ambari.server.state;
 
 import java.util.Map;
 
+import org.apache.ambari.server.AmbariException;
+import org.apache.ambari.server.controller.ServiceResponse;
+
 public interface Service {
 
   public String getName();
-  
+
   public long getClusterId();
-  
-  public long getCurrentHostComponentMappingVersion();
 
-  public void setCurrentHostComponentMappingVersion(long version);
+  public Cluster getCluster();
 
-  public ServiceComponent getServiceComponent(String componentName);
+  public ServiceComponent getServiceComponent(String componentName)
+      throws AmbariException;
 
   public Map<String, ServiceComponent> getServiceComponents();
 
   public void addServiceComponents(Map<String, ServiceComponent> components);
 
+  public void addServiceComponent(ServiceComponent component);
+
+  public State getDesiredState();
+
+  public void setDesiredState(State state);
+
+  public Map<String, Config> getDesiredConfigs();
+
+  public void updateDesiredConfigs(Map<String, Config> configs);
+
+  public StackVersion getDesiredStackVersion();
+
+  public void setDesiredStackVersion(StackVersion stackVersion);
+
   public State getState();
-  
+
   public void setState(State state);
 
   public Map<String, Config> getConfigs();
 
   public void updateConfigs(Map<String, Config> configs);
-  
+
   public StackVersion getStackVersion();
-  
+
   public void setStackVersion(StackVersion stackVersion);
-  
+
+  public ServiceResponse convertToResponse();
+
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponent.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponent.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponent.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponent.java Mon Oct  8 01:37:59 2012
@@ -20,31 +20,53 @@ package org.apache.ambari.server.state;
 
 import java.util.Map;
 
+import org.apache.ambari.server.AmbariException;
+import org.apache.ambari.server.controller.ServiceComponentResponse;
 
 public interface ServiceComponent {
 
   public String getName();
-  
+
   public String getServiceName();
 
   public long getClusterId();
-  
+
+  // TODO
+  public String getClusterName();
+
+  public State getDesiredState();
+
+  public void setDesiredState(State state);
+
+  public Map<String, Config> getDesiredConfigs();
+
+  public void updateDesiredConfigs(Map<String, Config> configs);
+
+  public StackVersion getDesiredStackVersion();
+
+  public void setDesiredStackVersion(StackVersion stackVersion);
+
   public State getState();
-  
+
   public void setState(State state);
 
   public Map<String, Config> getConfigs();
 
   public void updateConfigs(Map<String, Config> configs);
-  
+
   public StackVersion getStackVersion();
-  
+
   public void setStackVersion(StackVersion stackVersion);
-  
+
   public Map<String, ServiceComponentHost> getServiceComponentHosts();
-  
-  public ServiceComponentHost getServiceComponentHost(String hostname);
-  
+
+  public ServiceComponentHost getServiceComponentHost(String hostname)
+      throws AmbariException;
+
   public void addServiceComponentHosts(Map<String, ServiceComponentHost>
       hostComponents);
+
+  public void addServiceComponentHost(ServiceComponentHost hostComponent);
+
+  public ServiceComponentResponse convertToResponse();
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentHost.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentHost.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentHost.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentHost.java Mon Oct  8 01:37:59 2012
@@ -21,8 +21,9 @@ package org.apache.ambari.server.state;
 import java.util.List;
 import java.util.Map;
 
+import org.apache.ambari.server.controller.ServiceComponentHostResponse;
 import org.apache.ambari.server.state.fsm.InvalidStateTransitonException;
-import org.apache.ambari.server.state.live.job.Job;
+import org.apache.ambari.server.state.job.Job;
 
 
 public interface ServiceComponentHost {
@@ -33,6 +34,11 @@ public interface ServiceComponentHost {
   public long getClusterId();
 
   /**
+   * Get the Cluster that this object maps to
+   */
+  public String getClusterName();
+
+  /**
    * Get the Service this object maps to
    * @return Name of the Service
    */
@@ -65,16 +71,30 @@ public interface ServiceComponentHost {
   public void handleEvent(ServiceComponentHostEvent event)
       throws InvalidStateTransitonException;
 
+  public State getDesiredState();
+
+  public void setDesiredState(State state);
+
+  public Map<String, Config> getDesiredConfigs();
+
+  public void updateDesiredConfigs(Map<String, Config> configs);
+
+  public StackVersion getDesiredStackVersion();
+
+  public void setDesiredStackVersion(StackVersion stackVersion);
+
   public State getState();
-  
+
   public void setState(State state);
 
   public Map<String, Config> getConfigs();
 
   public void updateConfigs(Map<String, Config> configs);
-  
+
   public StackVersion getStackVersion();
-  
+
   public void setStackVersion(StackVersion stackVersion);
-  
+
+  public ServiceComponentHostResponse convertToResponse();
+
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentImpl.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentImpl.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentImpl.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceComponentImpl.java Mon Oct  8 01:37:59 2012
@@ -22,46 +22,51 @@ import java.util.Collections;
 import java.util.HashMap;
 import java.util.Map;
 
+import org.apache.ambari.server.AmbariException;
+import org.apache.ambari.server.ServiceComponentHostNotFoundException;
+import org.apache.ambari.server.controller.ServiceComponentResponse;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 
 public class ServiceComponentImpl implements ServiceComponent {
 
+  private final static Logger LOG =
+      LoggerFactory.getLogger(ServiceComponentImpl.class);
+
   private final Service service;
-  
   private final String componentName;
-  
+
   private State state;
-  
   private Map<String, Config> configs;
+  private StackVersion stackVersion;
+
+  private State desiredState;
+  private Map<String, Config>  desiredConfigs;
+  private StackVersion desiredStackVersion;
 
   private Map<String, ServiceComponentHost> hostComponents;
-  
-  private StackVersion stackVersion;
+
 
   private void init() {
     // TODO
-    // initialize from DB 
+    // initialize from DB
   }
-  
+
   public ServiceComponentImpl(Service service,
-      String componentName, State state, Map<String, Config> configs) {
+      String componentName) {
     this.service = service;
     this.componentName = componentName;
-    this.state = state;
-    if (configs != null) {
-      this.configs = configs;
-    } else {
-      this.configs = new HashMap<String, Config>();
-    }
+    this.state = State.INIT;
+    this.desiredState = State.INIT;
+    this.configs = new HashMap<String, Config>();
+    this.desiredConfigs = new HashMap<String, Config>();
+    this.stackVersion = new StackVersion("");
+    this.desiredStackVersion = new StackVersion("");
     this.hostComponents = new HashMap<String, ServiceComponentHost>();
     init();
   }
-  
-  public ServiceComponentImpl(Service service,
-      String componentName) {
-    this(service, componentName, State.INIT, null);
-  }
-  
-  
+
+
   @Override
   public synchronized String getName() {
     return componentName;
@@ -84,6 +89,15 @@ public class ServiceComponentImpl implem
 
   @Override
   public synchronized void setState(State state) {
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting State of Service"
+          + ", clusterName=" + service.getCluster().getClusterName()
+          + ", clusterId=" + service.getCluster().getClusterId()
+          + ", serviceName=" + service.getName()
+          + ", serviceComponentName=" + componentName
+          + ", oldState=" + this.state
+          + ", newState=" + state);
+    }
     this.state = state;
   }
 
@@ -104,6 +118,15 @@ public class ServiceComponentImpl implem
 
   @Override
   public synchronized void setStackVersion(StackVersion stackVersion) {
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting StackVersion of Service"
+          + ", clusterName=" + service.getCluster().getClusterName()
+          + ", clusterId=" + service.getCluster().getClusterId()
+          + ", serviceName=" + service.getName()
+          + ", serviceComponentName=" + componentName
+          + ", oldStackVersion=" + this.stackVersion
+          + ", newStackVersion=" + stackVersion);
+    }
     this.stackVersion = stackVersion;
   }
 
@@ -116,13 +139,105 @@ public class ServiceComponentImpl implem
   @Override
   public synchronized void addServiceComponentHosts(
       Map<String, ServiceComponentHost> hostComponents) {
-    // TODO
-    this.hostComponents.putAll(hostComponents);
+    // TODO validation
+    for (ServiceComponentHost sch : hostComponents.values()) {
+      addServiceComponentHost(sch);
+    }
   }
 
   @Override
-  public ServiceComponentHost getServiceComponentHost(String hostname) {
+  public synchronized void addServiceComponentHost(
+      ServiceComponentHost hostComponent) {
+    // TODO validation
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Adding a ServiceComponentHost to ServiceComponent"
+          + ", clusterName=" + service.getCluster().getClusterName()
+          + ", clusterId=" + service.getCluster().getClusterId()
+          + ", serviceName=" + service.getName()
+          + ", serviceComponentName=" + componentName
+          + ", hostname=" + hostComponent.getHostName());
+    }
+    this.hostComponents.put(hostComponent.getHostName(),
+        hostComponent);
+  }
+
+  @Override
+  public ServiceComponentHost getServiceComponentHost(String hostname)
+    throws AmbariException {
+    if (!hostComponents.containsKey(hostname)) {
+      throw new ServiceComponentHostNotFoundException(getClusterName(),
+          getServiceName(), componentName, hostname);
+    }
     return this.hostComponents.get(hostname);
   }
 
+  @Override
+  public synchronized State getDesiredState() {
+    return desiredState;
+  }
+
+  @Override
+  public synchronized void setDesiredState(State state) {
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting DesiredState of Service"
+          + ", clusterName=" + service.getCluster().getClusterName()
+          + ", clusterId=" + service.getCluster().getClusterId()
+          + ", serviceName=" + service.getName()
+          + ", serviceComponentName=" + componentName
+          + ", oldDesiredState=" + this.desiredState
+          + ", newDesiredState=" + state);
+    }
+    this.desiredState = state;
+  }
+
+  @Override
+  public synchronized Map<String, Config> getDesiredConfigs() {
+    return Collections.unmodifiableMap(desiredConfigs);
+  }
+
+  @Override
+  public synchronized void updateDesiredConfigs(Map<String, Config> configs) {
+    this.desiredConfigs.putAll(configs);
+  }
+
+  @Override
+  public synchronized StackVersion getDesiredStackVersion() {
+    return desiredStackVersion;
+  }
+
+  @Override
+  public synchronized void setDesiredStackVersion(StackVersion stackVersion) {
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting DesiredStackVersion of Service"
+          + ", clusterName=" + service.getCluster().getClusterName()
+          + ", clusterId=" + service.getCluster().getClusterId()
+          + ", serviceName=" + service.getName()
+          + ", serviceComponentName=" + componentName
+          + ", oldDesiredStackVersion=" + this.desiredStackVersion
+          + ", newDesiredStackVersion=" + stackVersion);
+    }
+    this.desiredStackVersion = stackVersion;
+  }
+
+  private synchronized Map<String, String> getConfigVersions() {
+    Map<String, String> configVersions = new HashMap<String, String>();
+    for (Config c : configs.values()) {
+      configVersions.put(c.getType(), c.getVersionTag());
+    }
+    return configVersions;
+  }
+
+  @Override
+  public ServiceComponentResponse convertToResponse() {
+    ServiceComponentResponse r  = new ServiceComponentResponse(
+        getClusterId(), service.getCluster().getClusterName(),
+        service.getName(), componentName, getConfigVersions());
+    return r;
+  }
+
+  @Override
+  public String getClusterName() {
+    return service.getCluster().getClusterName();
+  }
+
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceImpl.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceImpl.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceImpl.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/ServiceImpl.java Mon Oct  8 01:37:59 2012
@@ -22,44 +22,46 @@ import java.util.Collections;
 import java.util.HashMap;
 import java.util.Map;
 
+import org.apache.ambari.server.AmbariException;
+import org.apache.ambari.server.ServiceComponentNotFoundException;
+import org.apache.ambari.server.controller.ServiceResponse;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
 
 public class ServiceImpl implements Service {
 
+  private static final Logger LOG =
+      LoggerFactory.getLogger(ServiceImpl.class);
+
   private final Cluster cluster;
   private final String serviceName;
   private State state;
+  private State desiredState;
   private Map<String, Config> configs;
+  private Map<String, Config> desiredConfigs;
   private Map<String, ServiceComponent> components;
   private StackVersion stackVersion;
-  
+  private StackVersion desiredStackVersion;
+
   private void init() {
     // TODO
-    // initialize from DB 
+    // initialize from DB
   }
-  
-  public ServiceImpl(Cluster cluster, String serviceName,
-      State state, Map<String, Config> configs) {
+
+  public ServiceImpl(Cluster cluster, String serviceName) {
     this.cluster = cluster;
     this.serviceName = serviceName;
-    this.state = state;
-    if (configs != null) {
-      this.configs = configs;
-    } else {
-      this.configs = new HashMap<String, Config>();
-    }
+    this.state = State.INIT;
+    this.desiredState = State.INIT;
+    this.configs = new HashMap<String, Config>();
+    this.desiredConfigs = new HashMap<String, Config>();
+    this.stackVersion = new StackVersion("");
+    this.desiredStackVersion = new StackVersion("");
     this.components = new HashMap<String, ServiceComponent>();
     init();
   }
 
-  public ServiceImpl(Cluster cluster, String serviceName,
-      Map<String, Config> configs) {
-    this(cluster, serviceName, State.INIT, configs);
-  }
-  
-  public ServiceImpl(Cluster cluster, String serviceName) {
-    this(cluster, serviceName, State.INIT, null);
-  }
-  
   @Override
   public String getName() {
     return serviceName;
@@ -71,12 +73,6 @@ public class ServiceImpl implements Serv
   }
 
   @Override
-  public synchronized long getCurrentHostComponentMappingVersion() {
-    // TODO Auto-generated method stub
-    return 0;
-  }
-
-  @Override
   public synchronized Map<String, ServiceComponent> getServiceComponents() {
     return Collections.unmodifiableMap(components);
   }
@@ -88,6 +84,15 @@ public class ServiceImpl implements Serv
 
   @Override
   public synchronized void setState(State state) {
+    if (state == null) {
+      // TODO throw error?
+      return;
+    }
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting state of Service"
+          + ", oldState=" + this.state
+          + ", newState=" + state);
+    }
     this.state = state;
   }
 
@@ -98,6 +103,18 @@ public class ServiceImpl implements Serv
 
   @Override
   public synchronized void setStackVersion(StackVersion stackVersion) {
+    if (stackVersion == null) {
+      // TODO throw error?
+      return;
+    }
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting StackVersion of Service"
+          + ", clusterName=" + cluster.getClusterName()
+          + ", clusterId=" + cluster.getClusterId()
+          + ", serviceName=" + serviceName
+          + ", oldStackVersion=" + this.stackVersion
+          + ", newStackVersion=" + stackVersion);
+    }
     this.stackVersion = stackVersion;
   }
 
@@ -112,19 +129,114 @@ public class ServiceImpl implements Serv
   }
 
   @Override
-  public synchronized void setCurrentHostComponentMappingVersion(long version) {
-    // TODO Auto-generated method stub    
+  public synchronized void addServiceComponents(
+      Map<String, ServiceComponent> components) {
+    for (ServiceComponent sc : components.values()) {
+      addServiceComponent(sc);
+    }
   }
 
   @Override
-  public synchronized void addServiceComponents(
-      Map<String, ServiceComponent> components) {
-    this.components.putAll(components);
+  public synchronized void addServiceComponent(ServiceComponent component) {
+    // TODO validation
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Adding a ServiceComponent to Service"
+          + ", clusterName=" + cluster.getClusterName()
+          + ", clusterId=" + cluster.getClusterId()
+          + ", serviceName=" + serviceName
+          + ", serviceComponentName=" + component.getName());
+    }
+    this.components.put(component.getName(), component);
   }
 
   @Override
-  public ServiceComponent getServiceComponent(String componentName) {
+  public ServiceComponent getServiceComponent(String componentName)
+      throws AmbariException {
+    if (!components.containsKey(componentName)) {
+      throw new ServiceComponentNotFoundException(cluster.getClusterName(),
+          serviceName,
+          componentName);
+    }
     return this.components.get(componentName);
   }
 
+  @Override
+  public synchronized State getDesiredState() {
+    return desiredState;
+  }
+
+  @Override
+  public synchronized void setDesiredState(State state) {
+    if (state == null) {
+      // TODO throw error?
+      return;
+    }
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting DesiredState of Service"
+          + ", clusterName=" + cluster.getClusterName()
+          + ", clusterId=" + cluster.getClusterId()
+          + ", serviceName=" + serviceName
+          + ", oldDesiredState=" + this.desiredState
+          + ", newDesiredState=" + state);
+    }
+    this.desiredState = state;
+  }
+
+  @Override
+  public synchronized Map<String, Config> getDesiredConfigs() {
+    return Collections.unmodifiableMap(desiredConfigs);
+  }
+
+  @Override
+  public synchronized void updateDesiredConfigs(Map<String, Config> configs) {
+    this.desiredConfigs.putAll(configs);
+  }
+
+  @Override
+  public synchronized StackVersion getDesiredStackVersion() {
+    return desiredStackVersion;
+  }
+
+  @Override
+  public synchronized void setDesiredStackVersion(StackVersion stackVersion) {
+    if (stackVersion == null) {
+      // TODO throw error?
+      return;
+    }
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Setting DesiredStackVersion of Service"
+          + ", clusterName=" + cluster.getClusterName()
+          + ", clusterId=" + cluster.getClusterId()
+          + ", serviceName=" + serviceName
+          + ", oldDesiredStackVersion=" + this.desiredStackVersion
+          + ", newDesiredStackVersion=" + stackVersion);
+    }
+    this.desiredStackVersion = stackVersion;
+  }
+
+  private synchronized Map<String, String> getConfigVersions() {
+    Map<String, String> configVersions = new HashMap<String, String>();
+    for (Config c : configs.values()) {
+      configVersions.put(c.getType(), c.getVersionTag());
+    }
+    return configVersions;
+  }
+
+  @Override
+  public synchronized ServiceResponse convertToResponse() {
+    ServiceResponse r = new ServiceResponse(cluster.getClusterId(),
+        cluster.getClusterName(),
+        serviceName,
+        stackVersion.getStackVersion(),
+        getConfigVersions(),
+        desiredStackVersion.getStackVersion(),
+        desiredState.toString());
+    return r;
+  }
+
+  @Override
+  public Cluster getCluster() {
+    return cluster;
+  }
+
 }

Modified: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/State.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/State.java?rev=1395430&r1=1395429&r2=1395430&view=diff
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/State.java (original)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/State.java Mon Oct  8 01:37:59 2012
@@ -75,13 +75,13 @@ public enum State {
    * State when wipeout fails
    */
   WIPEOUT_FAILED(13);
-  
+
   private final int state;
-  
+
   private State(int state) {
     this.state = state;
   }
-  
+
   public boolean isValidDesiredState() {
     switch (State.values()[this.state]) {
       case INIT:
@@ -93,7 +93,7 @@ public enum State {
         return false;
     }
   }
-  
+
   public boolean isInProgressState() {
     switch (State.values()[this.state]) {
       case INSTALLING:
@@ -106,5 +106,5 @@ public enum State {
         return false;
     }
   }
-  
+
 }

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterFactory.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterFactory.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterFactory.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterFactory.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,29 @@
+/**
+ * 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.ambari.server.state.cluster;
+
+import org.apache.ambari.server.orm.entities.ClusterEntity;
+import org.apache.ambari.server.state.Cluster;
+
+/**
+ * Factory interface for Guice injections
+ */
+public interface ClusterFactory {
+  Cluster create(ClusterEntity clusterEntity);
+}

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterImpl.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterImpl.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterImpl.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClusterImpl.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,267 @@
+/**
+ * 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.ambari.server.state.cluster;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.TreeMap;
+
+import org.apache.ambari.server.AmbariException;
+import org.apache.ambari.server.ServiceComponentHostNotFoundException;
+import org.apache.ambari.server.ServiceNotFoundException;
+import org.apache.ambari.server.controller.ClusterResponse;
+import org.apache.ambari.server.state.Cluster;
+import org.apache.ambari.server.state.Clusters;
+import org.apache.ambari.server.state.Config;
+import org.apache.ambari.server.state.Service;
+import org.apache.ambari.server.state.ServiceComponentHost;
+import org.apache.ambari.server.state.StackVersion;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class ClusterImpl implements Cluster {
+
+  private static final Logger LOG =
+      LoggerFactory.getLogger(ClusterImpl.class);
+
+  private final Clusters clusters;
+
+  private final long clusterId;
+
+  private String clusterName;
+
+  private StackVersion desiredStackVersion;
+
+  private Map<String, Service> services = new TreeMap<String, Service>();
+
+  /**
+   * [ Config Type -> [ Config Version Tag -> Config ] ]
+   */
+  private Map<String, Map<String, Config>> configs;
+
+  /**
+   * [ ServiceName -> [ ServiceComponentName -> [ HostName -> [ ... ] ] ] ]
+   */
+  private Map<String, Map<String, Map<String, ServiceComponentHost>>>
+      serviceComponentHosts;
+
+  /**
+   * [ HostName -> [ ... ] ]
+   */
+  private Map<String, List<ServiceComponentHost>>
+      serviceComponentHostsByHost;
+
+  public ClusterImpl(Clusters clusters, long clusterId, String clusterName) {
+    this.clusters = clusters;
+    this.clusterId = clusterId;
+    this.clusterName = clusterName;
+    this.serviceComponentHosts = new HashMap<String,
+        Map<String,Map<String,ServiceComponentHost>>>();
+    this.serviceComponentHostsByHost = new HashMap<String,
+        List<ServiceComponentHost>>();
+    this.desiredStackVersion = null;
+    this.configs = new HashMap<String, Map<String,Config>>();
+  }
+
+  public ServiceComponentHost getServiceComponentHost(String serviceName,
+      String serviceComponentName, String hostname) throws AmbariException {
+    if (!serviceComponentHosts.containsKey(serviceName)
+        || !serviceComponentHosts.get(serviceName)
+            .containsKey(serviceComponentName)
+        || !serviceComponentHosts.get(serviceName).get(serviceComponentName)
+            .containsKey(hostname)) {
+      throw new ServiceComponentHostNotFoundException(clusterName, serviceName,
+          serviceComponentName, hostname);
+    }
+    return serviceComponentHosts.get(serviceName).get(serviceComponentName)
+        .get(hostname);
+  }
+
+  @Override
+  public synchronized String getClusterName() {
+    return clusterName;
+  }
+
+  @Override
+  public synchronized void setClusterName(String clusterName) {
+    this.clusterName = clusterName;
+  }
+
+  synchronized void addServiceComponentHost(ServiceComponentHost svcCompHost)
+      throws AmbariException {
+    final String hostname = svcCompHost.getHostName();
+    final String serviceName = svcCompHost.getServiceName();
+    final String componentName = svcCompHost.getServiceComponentName();
+    Set<Cluster> cs = clusters.getClustersForHost(hostname);
+    boolean clusterFound = false;
+    for (Cluster c = cs.iterator().next(); ; cs.iterator().hasNext()) {
+      if (c.getClusterId() == this.clusterId) {
+        clusterFound = true;
+        break;
+      }
+    }
+    if (!clusterFound) {
+      throw new AmbariException("Host does not belong this cluster"
+          + ", hostname=" + hostname
+          + ", clusterName=" + clusterName
+          + ", clusterId=" + clusterId);
+    }
+
+    if (!serviceComponentHosts.containsKey(serviceName)) {
+      serviceComponentHosts.put(serviceName,
+          new HashMap<String, Map<String,ServiceComponentHost>>());
+    }
+    if (!serviceComponentHosts.get(serviceName).containsKey(componentName)) {
+      serviceComponentHosts.get(serviceName).put(componentName,
+          new HashMap<String, ServiceComponentHost>());
+    }
+
+    if (serviceComponentHosts.get(serviceName).get(componentName).
+        containsKey(hostname)) {
+      throw new AmbariException("Duplicate entry for ServiceComponentHost"
+          + ", serviceName=" + serviceName
+          + ", serviceComponentName" + componentName
+          + ", hostname= " + hostname);
+    }
+
+    if (!serviceComponentHostsByHost.containsKey(hostname)) {
+      serviceComponentHostsByHost.put(hostname,
+          new ArrayList<ServiceComponentHost>());
+    }
+
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Adding a new ServiceComponentHost"
+          + ", clusterName=" + clusterName
+          + ", clusterId=" + clusterId
+          + ", serviceName=" + serviceName
+          + ", serviceComponentName" + componentName
+          + ", hostname= " + hostname);
+    }
+
+    serviceComponentHosts.get(serviceName).get(componentName).put(hostname,
+        svcCompHost);
+    serviceComponentHostsByHost.get(hostname).add(svcCompHost);
+  }
+
+  @Override
+  public long getClusterId() {
+    return clusterId;
+  }
+
+  @Override
+  public synchronized List<ServiceComponentHost> getServiceComponentHosts(
+      String hostname) {
+    return Collections.unmodifiableList(
+        serviceComponentHostsByHost.get(hostname));
+  }
+
+  @Override
+  public synchronized void addService(Service service)
+      throws AmbariException {
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Adding a new Service"
+          + ", clusterName=" + clusterName
+          + ", clusterId=" + clusterId
+          + ", serviceName=" + service.getName());
+    }
+    if (services.containsKey(service.getName())) {
+      throw new AmbariException("Service already exists"
+          + ", clusterName=" + clusterName
+          + ", clusterId=" + clusterId
+          + ", serviceName=" + service.getName());
+    }
+    this.services.put(service.getName(), service);
+  }
+
+  @Override
+  public synchronized Service getService(String serviceName)
+      throws AmbariException {
+    if (!services.containsKey(serviceName)) {
+      throw new ServiceNotFoundException(clusterName, serviceName);
+    }
+    return services.get(serviceName);
+  }
+
+  @Override
+  public synchronized Map<String, Service> getServices() {
+    return Collections.unmodifiableMap(services);
+  }
+
+  @Override
+  public synchronized StackVersion getDesiredStackVersion() {
+    return desiredStackVersion;
+  }
+
+  @Override
+  public synchronized void setDesiredStackVersion(StackVersion stackVersion) {
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Changing DesiredStackVersion of Cluster"
+        + ", clusterName=" + clusterName
+        + ", clusterId=" + clusterId
+        + ", currentStackVersion=" + this.desiredStackVersion
+        + ", newStackVersion=" + stackVersion);
+    }
+    this.desiredStackVersion = stackVersion;
+  }
+
+  @Override
+  public synchronized Map<String, Config> getConfigsByType(String configType) {
+    return Collections.unmodifiableMap(configs.get(configType));
+  }
+
+  @Override
+  public synchronized Config getConfig(String configType, String versionTag) {
+    if (!configs.containsKey(configType)
+        || !configs.get(configType).containsKey(versionTag)) {
+      // TODO throw error
+    }
+    return configs.get(configType).get(versionTag);
+  }
+
+  @Override
+  public synchronized void addConfig(Config config) {
+    if (config.getType() == null
+        || config.getType().isEmpty()
+        || config.getVersionTag() == null
+        || config.getVersionTag().isEmpty()) {
+      // TODO throw error
+    }
+    if (!configs.containsKey(config.getType())) {
+      configs.put(config.getType(), new HashMap<String, Config>());
+    }
+
+    // TODO should we check for duplicates and throw an error?
+    // if (configs.get(config.getType()).containsKey(config.getVersionTag()))
+
+    configs.get(config.getType()).put(config.getVersionTag(), config);
+  }
+
+  @Override
+  public synchronized ClusterResponse convertToResponse() {
+    ClusterResponse r = new ClusterResponse(clusterId, clusterName,
+        new HashSet<String>(serviceComponentHostsByHost.keySet()));
+    return r;
+  }
+
+}

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClustersImpl.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClustersImpl.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClustersImpl.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/cluster/ClustersImpl.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,159 @@
+/**
+ * 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.ambari.server.state.cluster;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.ambari.server.AmbariException;
+import org.apache.ambari.server.ClusterNotFoundException;
+import org.apache.ambari.server.HostNotFoundException;
+import org.apache.ambari.server.state.Cluster;
+import org.apache.ambari.server.state.Clusters;
+import org.apache.ambari.server.state.Host;
+import org.apache.ambari.server.state.host.HostImpl;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+public class ClustersImpl implements Clusters {
+
+  private static final Logger LOG = LoggerFactory.getLogger(
+      ClustersImpl.class);
+
+  private Map<String, Cluster> clusters;
+  private Map<Long, Cluster> clustersById;
+  private Map<String, Host> hosts;
+  private Map<String, Set<Cluster>> hostClusterMap;
+
+  public ClustersImpl() {
+    clusters = new HashMap<String, Cluster>();
+    clustersById = new HashMap<Long, Cluster>();
+    hosts = new HashMap<String, Host>();
+    hostClusterMap = new HashMap<String, Set<Cluster>>();
+
+  }
+
+  @Override
+  public synchronized void addCluster(String clusterName)
+      throws AmbariException {
+    if (clusters.containsKey(clusterName)) {
+      throw new AmbariException("Duplicate entry for Cluster"
+          + ", clusterName= " + clusterName);
+    }
+    // TODO persist cluster into DB
+    // retrieve new cluster id
+    // add cluster id -> cluster mapping into clustersById
+    long clusterId = clusterName.hashCode();
+    Cluster impl = new ClusterImpl(this, clusterId, clusterName);
+    clusters.put(clusterName, impl);
+    clustersById.put(clusterId, impl);
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Adding a new cluster"
+          + ", clusterName=" + clusterName
+          + ", clusterId=" + clusterId);
+    }
+  }
+
+  @Override
+  public synchronized Cluster getCluster(String clusterName)
+      throws AmbariException {
+    if (!clusters.containsKey(clusterName)) {
+      throw new ClusterNotFoundException(clusterName);
+    }
+    return clusters.get(clusterName);
+  }
+
+  @Override
+  public synchronized List<Host> getHosts() {
+    return new ArrayList<Host>(hosts.values());
+  }
+
+  @Override
+  public synchronized Set<Cluster> getClustersForHost(String hostname)
+      throws AmbariException {
+    if (!hostClusterMap.containsKey(hostname)) {
+      throw new HostNotFoundException(hostname);
+    }
+    return Collections.unmodifiableSet(hostClusterMap.get(hostname));
+  }
+
+  @Override
+  public synchronized Host getHost(String hostname) throws AmbariException {
+    return hosts.get(hostname);
+  }
+
+  @Override
+  public synchronized void addHost(String hostname) throws AmbariException {
+    if (hosts.containsKey(hostname)) {
+      throw new AmbariException("Duplicate entry for Host"
+          + ", hostName= " + hostname);
+    }
+    hosts.put(hostname, new HostImpl(hostname));
+    hostClusterMap.put(hostname, new HashSet<Cluster>());
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Adding a host to Clusters"
+          + ", hostname=" + hostname);
+    }
+  }
+
+  @Override
+  public synchronized void mapHostToCluster(String hostname,
+      String clusterName) throws AmbariException {
+    Cluster c = getCluster(clusterName);
+    getHost(hostname);
+    if (!hostClusterMap.containsKey(hostname)) {
+      throw new HostNotFoundException(hostname);
+    }
+    hostClusterMap.get(hostname).add(c);
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Mapping a host to a cluster"
+          + ", clusterName=" + clusterName
+          + ", clusterId=" + c.getClusterId()
+          + ", hostname=" + hostname);
+    }
+  }
+
+  @Override
+  public synchronized Map<String, Cluster> getClusters() {
+    return Collections.unmodifiableMap(clusters);
+  }
+
+  @Override
+  public synchronized void mapHostsToCluster(List<String> hostnames,
+      String clusterName) throws AmbariException {
+    Cluster c = getCluster(clusterName);
+    for (String hostname : hostnames) {
+      if (!hostClusterMap.containsKey(hostname)) {
+        throw new HostNotFoundException(hostname);
+      }
+      hostClusterMap.get(hostname).add(c);
+      if (LOG.isDebugEnabled()) {
+        LOG.debug("Mapping a host to a cluster"
+            + ", clusterName=" + clusterName
+            + ", clusterId=" + c.getClusterId()
+            + ", hostname=" + hostname);
+      }
+    }
+  }
+}

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHealthyHeartbeatEvent.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHealthyHeartbeatEvent.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHealthyHeartbeatEvent.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHealthyHeartbeatEvent.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,41 @@
+/**
+ * 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.ambari.server.state.host;
+
+import org.apache.ambari.server.state.HostEvent;
+import org.apache.ambari.server.state.HostEventType;
+
+public class HostHealthyHeartbeatEvent extends HostEvent {
+
+  private final long heartbeatTime;
+
+  public HostHealthyHeartbeatEvent(String hostName, long heartbeatTime) {
+    super(hostName, HostEventType.HOST_HEARTBEAT_HEALTHY);
+    this.heartbeatTime = heartbeatTime;
+  }
+
+  /**
+   * @return the heartbeatTime
+   */
+  public long getHeartbeatTime() {
+    return heartbeatTime;
+  }
+
+}

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHeartbeatLostEvent.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHeartbeatLostEvent.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHeartbeatLostEvent.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostHeartbeatLostEvent.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,31 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+package org.apache.ambari.server.state.host;
+
+import org.apache.ambari.server.state.HostEvent;
+import org.apache.ambari.server.state.HostEventType;
+
+public class HostHeartbeatLostEvent extends HostEvent {
+
+  public HostHeartbeatLostEvent(String hostName) {
+    super(hostName, HostEventType.HOST_HEARTBEAT_LOST);
+  }
+
+}

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostImpl.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostImpl.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostImpl.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostImpl.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,786 @@
+/**
+ * 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.ambari.server.state.host;
+
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReadWriteLock;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+
+import org.apache.ambari.server.agent.DiskInfo;
+import org.apache.ambari.server.agent.HostInfo;
+import org.apache.ambari.server.controller.HostResponse;
+import org.apache.ambari.server.state.AgentVersion;
+import org.apache.ambari.server.state.Host;
+import org.apache.ambari.server.state.HostEvent;
+import org.apache.ambari.server.state.HostEventType;
+import org.apache.ambari.server.state.HostHealthStatus;
+import org.apache.ambari.server.state.HostState;
+import org.apache.ambari.server.state.HostHealthStatus.HealthStatus;
+import org.apache.ambari.server.state.fsm.InvalidStateTransitonException;
+import org.apache.ambari.server.state.fsm.SingleArcTransition;
+import org.apache.ambari.server.state.fsm.StateMachine;
+import org.apache.ambari.server.state.fsm.StateMachineFactory;
+import org.apache.ambari.server.state.job.Job;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+public class HostImpl implements Host {
+
+  private static final Log LOG = LogFactory.getLog(HostImpl.class);
+
+  private final Lock readLock;
+  private final Lock writeLock;
+
+  /**
+   * Host hostname
+   */
+  private String hostName;
+
+  /**
+   * Host IP if ipv4 interface available
+   */
+  private String ipv4;
+
+  /**
+   * Host IP if ipv6 interface available
+   */
+  private String ipv6;
+
+  /**
+   * Count of cores on Host
+   */
+  private int cpuCount;
+
+  /**
+   * Os Architecture
+   */
+  private String osArch;
+
+  /**
+   * OS Type
+   */
+  private String osType;
+
+  /**
+   * OS Information
+   */
+  private String osInfo;
+
+  /**
+   * Amount of available memory for the Host
+   */
+  private long availableMemBytes;
+
+  /**
+   * Amount of physical memory for the Host
+   */
+  private long totalMemBytes;
+
+  /**
+   * Disks mounted on the Host
+   */
+  private List<DiskInfo> disksInfo;
+
+  /**
+   * Last heartbeat timestamp from the Host
+   */
+  private long lastHeartbeatTime;
+
+  /**
+   * Last registration timestamp for the Host
+   */
+  private long lastRegistrationTime;
+
+  /**
+   * Rack to which the Host belongs to
+   */
+  private String rackInfo;
+
+  /**
+   * Additional Host attributes
+   */
+  private Map<String, String> hostAttributes;
+
+  /**
+   * Version of agent running on the Host
+   */
+  private AgentVersion agentVersion;
+
+  /**
+   * Host Health Status
+   */
+  private HostHealthStatus healthStatus;
+
+  private static final StateMachineFactory
+    <HostImpl, HostState, HostEventType, HostEvent>
+      stateMachineFactory
+        = new StateMachineFactory<HostImpl, HostState, HostEventType, HostEvent>
+        (HostState.INIT)
+
+   // define the state machine of a Host
+
+   // Transition from INIT state
+   // when the initial registration request is received
+   .addTransition(HostState.INIT, HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostEventType.HOST_REGISTRATION_REQUEST, new HostRegistrationReceived())
+
+   // Transition from WAITING_FOR_STATUS_UPDATES state
+   // when the host has responded to its status update requests
+   // TODO this will create problems if the host is not healthy
+   // TODO Based on discussion with Jitendra, ignoring this for now
+   .addTransition(HostState.WAITING_FOR_HOST_STATUS_UPDATES, HostState.HEALTHY,
+       HostEventType.HOST_STATUS_UPDATES_RECEIVED,
+       new HostStatusUpdatesReceivedTransition())
+   // when a normal heartbeat is received
+   .addTransition(HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostEventType.HOST_HEARTBEAT_HEALTHY)
+   // when a heartbeart denoting host as unhealthy is received
+   .addTransition(HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostEventType.HOST_HEARTBEAT_UNHEALTHY,
+       new HostHeartbeatReceivedTransition())
+
+   // Transitions from HEALTHY state
+   // when a normal heartbeat is received
+   .addTransition(HostState.HEALTHY, HostState.HEALTHY,
+       HostEventType.HOST_HEARTBEAT_HEALTHY,
+       new HostHeartbeatReceivedTransition())
+   // when a heartbeat is not received within the configured timeout period
+   .addTransition(HostState.HEALTHY, HostState.HEARTBEAT_LOST,
+       HostEventType.HOST_HEARTBEAT_LOST,
+       new HostHeartbeatLostTransition())
+   // when a heartbeart denoting host as unhealthy is received
+   .addTransition(HostState.HEALTHY, HostState.UNHEALTHY,
+       HostEventType.HOST_HEARTBEAT_UNHEALTHY,
+       new HostBecameUnhealthyTransition())
+   // if a new registration request is received
+   .addTransition(HostState.HEALTHY,
+       HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostEventType.HOST_REGISTRATION_REQUEST, new HostRegistrationReceived())
+
+   // Transitions from UNHEALTHY state
+   // when a normal heartbeat is received
+   .addTransition(HostState.UNHEALTHY, HostState.HEALTHY,
+       HostEventType.HOST_HEARTBEAT_HEALTHY,
+       new HostBecameHealthyTransition())
+   // when a heartbeart denoting host as unhealthy is received
+   .addTransition(HostState.UNHEALTHY, HostState.UNHEALTHY,
+       HostEventType.HOST_HEARTBEAT_UNHEALTHY,
+       new HostHeartbeatReceivedTransition())
+   // when a heartbeat is not received within the configured timeout period
+   .addTransition(HostState.UNHEALTHY, HostState.HEARTBEAT_LOST,
+       HostEventType.HOST_HEARTBEAT_LOST,
+       new HostHeartbeatLostTransition())
+   // if a new registration request is received
+   .addTransition(HostState.UNHEALTHY,
+       HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostEventType.HOST_REGISTRATION_REQUEST, new HostRegistrationReceived())
+
+   // Transitions from HEARTBEAT_LOST state
+   // when a heartbeat is not received within the configured timeout period
+   .addTransition(HostState.HEARTBEAT_LOST, HostState.HEARTBEAT_LOST,
+       HostEventType.HOST_HEARTBEAT_LOST)
+   // if a new registration request is received
+   .addTransition(HostState.HEARTBEAT_LOST,
+       HostState.WAITING_FOR_HOST_STATUS_UPDATES,
+       HostEventType.HOST_REGISTRATION_REQUEST, new HostRegistrationReceived())
+
+   .installTopology();
+
+  private final StateMachine<HostState, HostEventType, HostEvent> stateMachine;
+
+  public HostImpl(String hostName) {
+    super();
+    this.hostName = hostName;
+    this.stateMachine = stateMachineFactory.make(this);
+    ReadWriteLock rwLock = new ReentrantReadWriteLock();
+    this.readLock = rwLock.readLock();
+    this.writeLock = rwLock.writeLock();
+    this.healthStatus = new HostHealthStatus(HealthStatus.UNKNOWN, "");
+  }
+
+  static class HostRegistrationReceived
+      implements SingleArcTransition<HostImpl, HostEvent> {
+
+    @Override
+    public void transition(HostImpl host, HostEvent event) {
+      HostRegistrationRequestEvent e = (HostRegistrationRequestEvent) event;
+      host.importHostInfo(e.hostInfo);
+      host.setLastRegistrationTime(e.registrationTime);
+      host.setAgentVersion(e.agentVersion);
+    }
+  }
+
+  static class HostStatusUpdatesReceivedTransition
+      implements SingleArcTransition<HostImpl, HostEvent> {
+
+    @Override
+    public void transition(HostImpl host, HostEvent event) {
+      HostStatusUpdatesReceivedEvent e = (HostStatusUpdatesReceivedEvent)event;
+      // TODO Audit logs
+      LOG.debug("Host transition to host status updates received state"
+          + ", host=" + e.getHostName()
+          + ", heartbeatTime=" + e.getTimestamp());
+      host.getHealthStatus().setHealthStatus(HealthStatus.HEALTHY);
+    }
+  }
+
+  static class HostHeartbeatReceivedTransition
+    implements SingleArcTransition<HostImpl, HostEvent> {
+
+    @Override
+    public void transition(HostImpl host, HostEvent event) {
+      long heartbeatTime = 0;
+      switch (event.getType()) {
+        case HOST_HEARTBEAT_HEALTHY:
+          heartbeatTime =
+            ((HostHealthyHeartbeatEvent)event).getHeartbeatTime();
+          break;
+        case HOST_HEARTBEAT_UNHEALTHY:
+          heartbeatTime =
+            ((HostUnhealthyHeartbeatEvent)event).getHeartbeatTime();
+          break;
+        default:
+          break;
+      }
+      if (0 == heartbeatTime) {
+        // TODO handle error
+      }
+      host.setLastHeartbeatTime(heartbeatTime);
+    }
+  }
+
+  static class HostBecameHealthyTransition
+      implements SingleArcTransition<HostImpl, HostEvent> {
+
+    @Override
+    public void transition(HostImpl host, HostEvent event) {
+      HostHealthyHeartbeatEvent e = (HostHealthyHeartbeatEvent) event;
+      host.setLastHeartbeatTime(e.getHeartbeatTime());
+      // TODO Audit logs
+      LOG.debug("Host transitioned to a healthy state"
+          + ", host=" + e.getHostName()
+          + ", heartbeatTime=" + e.getHeartbeatTime());
+      host.getHealthStatus().setHealthStatus(HealthStatus.HEALTHY);
+    }
+  }
+
+  static class HostBecameUnhealthyTransition
+      implements SingleArcTransition<HostImpl, HostEvent> {
+
+    @Override
+    public void transition(HostImpl host, HostEvent event) {
+      HostUnhealthyHeartbeatEvent e = (HostUnhealthyHeartbeatEvent) event;
+      host.setLastHeartbeatTime(e.getHeartbeatTime());
+      // TODO Audit logs
+      LOG.debug("Host transitioned to an unhealthy state"
+          + ", host=" + e.getHostName()
+          + ", heartbeatTime=" + e.getHeartbeatTime()
+          + ", healthStatus=" + e.getHealthStatus());
+      host.setHealthStatus(e.getHealthStatus());
+    }
+  }
+
+  static class HostHeartbeatLostTransition
+      implements SingleArcTransition<HostImpl, HostEvent> {
+
+    @Override
+    public void transition(HostImpl host, HostEvent event) {
+      HostHeartbeatLostEvent e = (HostHeartbeatLostEvent) event;
+      // TODO Audit logs
+      LOG.debug("Host transitioned to heartbeat lost state"
+          + ", host=" + e.getHostName()
+          + ", lastHeartbeatTime=" + host.getLastHeartbeatTime());
+      host.getHealthStatus().setHealthStatus(HealthStatus.UNKNOWN);
+    }
+  }
+
+  void importHostInfo(HostInfo hostInfo) {
+    try {
+      writeLock.lock();
+      this.hostName = hostInfo.getHostName();
+      this.availableMemBytes = hostInfo.getFreeMemory();
+      this.totalMemBytes = hostInfo.getMemoryTotal();
+      this.cpuCount = hostInfo.getProcessorCount();
+      this.osArch = hostInfo.getArchitecture();
+      this.osType = hostInfo.getOS();
+      this.disksInfo = hostInfo.getMounts();
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public HostState getState() {
+    try {
+      readLock.lock();
+      return stateMachine.getCurrentState();
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setState(HostState state) {
+    try {
+      writeLock.lock();
+      stateMachine.setCurrentState(state);
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public void handleEvent(HostEvent event)
+      throws InvalidStateTransitonException {
+    if (LOG.isDebugEnabled()) {
+      LOG.debug("Handling Host event, eventType=" + event.getType().name()
+          + ", event=" + event.toString());
+    }
+    HostState oldState = getState();
+    try {
+      writeLock.lock();
+      try {
+        stateMachine.doTransition(event.getType(), event);
+      } catch (InvalidStateTransitonException e) {
+        LOG.error("Can't handle Host event at current state"
+            + ", host=" + this.getHostName()
+            + ", currentState=" + oldState
+            + ", eventType=" + event.getType()
+            + ", event=" + event);
+        throw e;
+      }
+    }
+    finally {
+      writeLock.unlock();
+    }
+    if (oldState != getState()) {
+      if (LOG.isDebugEnabled()) {
+        LOG.debug("Host transitioned to a new state"
+            + ", host=" + this.getHostName()
+            + ", oldState=" + oldState
+            + ", currentState=" + getState()
+            + ", eventType=" + event.getType().name()
+            + ", event=" + event);
+      }
+    }
+  }
+
+  @Override
+  public String getHostName() {
+    try {
+      readLock.lock();
+      return hostName;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setHostName(String hostName) {
+    try {
+      writeLock.lock();
+      this.hostName = hostName;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public String getIPv4() {
+    try {
+      readLock.lock();
+      return ipv4;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setIPv4(String ip) {
+    try {
+      writeLock.lock();
+      this.ipv4 = ip;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public String getIPv6() {
+    try {
+      readLock.lock();
+      return ipv6;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setIPv6(String ip) {
+    try {
+      writeLock.lock();
+      this.ipv6 = ip;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public int getCpuCount() {
+    try {
+      readLock.lock();
+      return cpuCount;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setCpuCount(int cpuCount) {
+    try {
+      writeLock.lock();
+      this.cpuCount = cpuCount;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public long getTotalMemBytes() {
+    try {
+      readLock.lock();
+      return totalMemBytes;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setTotalMemBytes(long totalMemBytes) {
+    try {
+      writeLock.lock();
+      this.totalMemBytes = totalMemBytes;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public long getAvailableMemBytes() {
+    try {
+      readLock.lock();
+      return availableMemBytes;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setAvailableMemBytes(long availableMemBytes) {
+    try {
+      writeLock.lock();
+      this.availableMemBytes = availableMemBytes;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public String getOsArch() {
+    try {
+      readLock.lock();
+      return osArch;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setOsArch(String osArch) {
+    try {
+      writeLock.lock();
+      this.osArch = osArch;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public String getOsInfo() {
+    try {
+      readLock.lock();
+      return osInfo;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setOsInfo(String osInfo) {
+    try {
+      writeLock.lock();
+      this.osInfo = osInfo;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public String getOsType() {
+    try {
+      readLock.lock();
+      return osType;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setOsType(String osType) {
+    try {
+      writeLock.lock();
+      this.osType = osType;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public List<DiskInfo> getDisksInfo() {
+    try {
+      readLock.lock();
+      return Collections.unmodifiableList(disksInfo);
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setDisksInfo(List<DiskInfo> disksInfo) {
+    try {
+      writeLock.lock();
+      this.disksInfo = disksInfo;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public HostHealthStatus getHealthStatus() {
+    try {
+      readLock.lock();
+      return healthStatus;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setHealthStatus(HostHealthStatus healthStatus) {
+    try {
+      writeLock.lock();
+      this.healthStatus = healthStatus;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public Map<String, String> getHostAttributes() {
+    try {
+      readLock.lock();
+      return Collections.unmodifiableMap(hostAttributes);
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setHostAttributes(Map<String, String> hostAttributes) {
+    try {
+      writeLock.lock();
+      this.hostAttributes.putAll(hostAttributes);
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public String getRackInfo() {
+    try {
+      readLock.lock();
+      return rackInfo;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setRackInfo(String rackInfo) {
+    try {
+      writeLock.lock();
+      this.rackInfo = rackInfo;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public long getLastRegistrationTime() {
+    try {
+      readLock.lock();
+      return lastRegistrationTime;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setLastRegistrationTime(long lastRegistrationTime) {
+    try {
+      writeLock.lock();
+      this.lastRegistrationTime = lastRegistrationTime;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public long getLastHeartbeatTime() {
+    try {
+      readLock.lock();
+      return lastHeartbeatTime;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setLastHeartbeatTime(long lastHeartbeatTime) {
+    try {
+      writeLock.lock();
+      this.lastHeartbeatTime = lastHeartbeatTime;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public AgentVersion getAgentVersion() {
+    try {
+      readLock.lock();
+      return agentVersion;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+  @Override
+  public void setAgentVersion(AgentVersion agentVersion) {
+    try {
+      writeLock.lock();
+      this.agentVersion = agentVersion;
+    }
+    finally {
+      writeLock.unlock();
+    }
+  }
+
+  @Override
+  public List<Job> getJobs() {
+    // TODO Auto-generated method stub
+    return null;
+  }
+
+  @Override
+  public long getTimeInState() {
+    // TODO Auto-generated method stub
+    return 0;
+  }
+
+  @Override
+  public synchronized HostResponse convertToResponse() {
+    HostResponse r = new HostResponse(hostName);
+    try {
+      readLock.lock();
+
+      r.setAgentVersion(agentVersion);
+      r.setAvailableMemBytes(availableMemBytes);
+      r.setCpuCount(cpuCount);
+      r.setDisksInfo(getDisksInfo());
+      r.setHealthStatus(healthStatus);
+      r.setHostAttributes(getHostAttributes());
+      r.setIpv4(ipv4);
+      r.setIpv6(ipv6);
+      r.setLastHeartbeatTime(lastHeartbeatTime);
+      r.setLastRegistrationTime(lastRegistrationTime);
+      r.setOsArch(osArch);
+      r.setOsInfo(osInfo);
+      r.setOsType(osType);
+      r.setRackInfo(rackInfo);
+      r.setTotalMemBytes(totalMemBytes);
+
+      return r;
+    }
+    finally {
+      readLock.unlock();
+    }
+  }
+
+}

Added: incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostRegistrationRequestEvent.java
URL: http://svn.apache.org/viewvc/incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostRegistrationRequestEvent.java?rev=1395430&view=auto
==============================================================================
--- incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostRegistrationRequestEvent.java (added)
+++ incubator/ambari/branches/AMBARI-666/ambari-server/src/main/java/org/apache/ambari/server/state/host/HostRegistrationRequestEvent.java Mon Oct  8 01:37:59 2012
@@ -0,0 +1,42 @@
+/**
+ * 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.ambari.server.state.host;
+
+import org.apache.ambari.server.agent.HostInfo;
+import org.apache.ambari.server.state.AgentVersion;
+import org.apache.ambari.server.state.HostEvent;
+import org.apache.ambari.server.state.HostEventType;
+
+public class HostRegistrationRequestEvent extends HostEvent {
+
+  final long registrationTime;
+
+  final HostInfo hostInfo;
+
+  final AgentVersion agentVersion;
+
+  public HostRegistrationRequestEvent(String hostName,
+      AgentVersion agentVersion, long registrationTime, HostInfo hostInfo) {
+    super(hostName, HostEventType.HOST_REGISTRATION_REQUEST);
+    this.registrationTime = registrationTime;
+    this.hostInfo = hostInfo;
+    this.agentVersion = agentVersion;
+  }
+
+}