Extracted interface for Binding.

git-svn-id: https://google-guice.googlecode.com/svn/trunk@217 d779f126-a31b-0410-b53b-1d3aecad763e
diff --git a/src/com/google/inject/BinderImpl.java b/src/com/google/inject/BinderImpl.java
index d4b01de..e4dd97a 100644
--- a/src/com/google/inject/BinderImpl.java
+++ b/src/com/google/inject/BinderImpl.java
@@ -259,7 +259,7 @@
     stopwatch.resetAndLog(logger, "Configuration");
 
     // Create the container.
-    Map<Key<?>, Binding<?>> bindings = new HashMap<Key<?>, Binding<?>>();
+    Map<Key<?>, BindingImpl<?>> bindings = new HashMap<Key<?>, BindingImpl<?>>();
     container = new ContainerImpl(
         proxyFactoryBuilder.create(), bindings, scopes);
     container.setErrorHandler(configurationErrorHandler);
@@ -340,14 +340,14 @@
       return;
     }
 
-    Binding<? extends T> destination = container.getBinding(destinationKey);
+    BindingImpl<? extends T> destination = container.getBinding(destinationKey);
     if (destination == null) {
       addError(builder.getSource(), ErrorMessages.LINK_DESTINATION_NOT_FOUND,
           destinationKey);
       return;
     }
 
-    Binding<?> binding = Binding.newInstance(container, builder.getKey(),
+    BindingImpl<?> binding = BindingImpl.newInstance(container, builder.getKey(),
         builder.getSource(), destination.getInternalFactory());
 
     putBinding(binding);
@@ -364,8 +364,8 @@
     final Key<T> key = builder.getKey();
     final InternalFactory<? extends T> factory
         = builder.getInternalFactory(container);
-    Binding<?> binding
-        = Binding.newInstance(container, key, builder.getSource(), factory);
+    BindingImpl<?> binding
+        = BindingImpl.newInstance(container, key, builder.getSource(), factory);
 
     putBinding(binding);
 
@@ -398,9 +398,9 @@
     }
   }
 
-  void putBinding(Binding<?> binding) {
+  void putBinding(BindingImpl<?> binding) {
     Key<?> key = binding.getKey();
-    Map<Key<?>, Binding<?>> bindings = container.internalBindings();
+    Map<Key<?>, BindingImpl<?>> bindings = container.internalBindings();
     Binding<?> original = bindings.get(key);
 
     // Binding to Provider<?> is not allowed.
diff --git a/src/com/google/inject/Binding.java b/src/com/google/inject/Binding.java
index 623fcdc..c423cac 100644
--- a/src/com/google/inject/Binding.java
+++ b/src/com/google/inject/Binding.java
@@ -16,76 +16,26 @@
 
 package com.google.inject;
 
-import com.google.inject.util.ToStringBuilder;
-
 /**
  * A binding from a {@link Key} (type and name) to a provider.
  *
  * @author crazybob@google.com (Bob Lee)
  */
-public class Binding<T> {
-
-  final ContainerImpl container;
-  final Key<T> key;
-  final Object source;
-  final InternalFactory<? extends T> internalFactory;
-
-  Binding(ContainerImpl container, Key<T> key, Object source,
-      InternalFactory<? extends T> internalFactory) {
-    this.container = container;
-    this.key = key;
-    this.source = source;
-    this.internalFactory = internalFactory;
-  }
+public interface Binding<T> {
 
   /**
    * Gets the key for this binding.
    */
-  public Key<T> getKey() {
-    return key;
-  }
+  Key<T> getKey();
 
   /**
    * Gets the source object, an arbitrary object which points back to the
    * configuration which resulted in this binding.
    */
-  public Object getSource() {
-    return source;
-  }
-
-  volatile Provider<T> provider;
+  Object getSource();
 
   /**
    * Gets the provider which returns instances of {@code T}.
    */
-  public Provider<T> getProvider() {
-    if (provider == null) {
-      provider = container.getProvider(key);
-    }
-    return provider;
-  }
-
-  InternalFactory<? extends T> getInternalFactory() {
-    return internalFactory;
-  }
-
-  static <T> Binding<T> newInstance(ContainerImpl container, Key<T> key,
-      Object source, InternalFactory<? extends T> internalFactory) {
-    return new Binding<T>(container, key, source, internalFactory);
-  }
-
-  /**
-   * Is this a constant binding?
-   */
-  boolean isConstant() {
-    return internalFactory instanceof ConstantFactory<?>;
-  }
-
-  public String toString() {
-    return new ToStringBuilder(Binding.class)
-        .add("key", key)
-        .add("source", source)
-        .add("provider", internalFactory)
-        .toString();
-  }
-}
\ No newline at end of file
+  Provider<T> getProvider();
+}
diff --git a/src/com/google/inject/BindingImpl.java b/src/com/google/inject/BindingImpl.java
new file mode 100644
index 0000000..4e21de6
--- /dev/null
+++ b/src/com/google/inject/BindingImpl.java
@@ -0,0 +1,79 @@
+/**
+ * Copyright (C) 2006 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.inject;
+
+import com.google.inject.util.ToStringBuilder;
+
+/**
+ * @author crazybob@google.com (Bob Lee)
+ */
+class BindingImpl<T> implements Binding<T> {
+
+  final ContainerImpl container;
+  final Key<T> key;
+  final Object source;
+  final InternalFactory<? extends T> internalFactory;
+
+  BindingImpl(ContainerImpl container, Key<T> key, Object source,
+      InternalFactory<? extends T> internalFactory) {
+    this.container = container;
+    this.key = key;
+    this.source = source;
+    this.internalFactory = internalFactory;
+  }
+
+  public Key<T> getKey() {
+    return key;
+  }
+
+  public Object getSource() {
+    return source;
+  }
+
+  volatile Provider<T> provider;
+
+  public Provider<T> getProvider() {
+    if (provider == null) {
+      provider = container.getProvider(key);
+    }
+    return provider;
+  }
+
+  InternalFactory<? extends T> getInternalFactory() {
+    return internalFactory;
+  }
+
+  static <T> BindingImpl<T> newInstance(ContainerImpl container, Key<T> key,
+      Object source, InternalFactory<? extends T> internalFactory) {
+    return new BindingImpl<T>(container, key, source, internalFactory);
+  }
+
+  /**
+   * Is this a constant binding?
+   */
+  boolean isConstant() {
+    return internalFactory instanceof ConstantFactory<?>;
+  }
+
+  public String toString() {
+    return new ToStringBuilder(BindingImpl.class)
+        .add("key", key)
+        .add("source", source)
+        .add("provider", internalFactory)
+        .toString();
+  }
+}
\ No newline at end of file
diff --git a/src/com/google/inject/ConstantBindingBuilderImpl.java b/src/com/google/inject/ConstantBindingBuilderImpl.java
index 55d68e7..5a7e700 100644
--- a/src/com/google/inject/ConstantBindingBuilderImpl.java
+++ b/src/com/google/inject/ConstantBindingBuilderImpl.java
@@ -83,7 +83,7 @@
     }
   }
 
-  Binding<?> createBinding(ContainerImpl container) {
+  BindingImpl<?> createBinding(ContainerImpl container) {
     return bindingInfo.createBinding(container);
   }
 
@@ -102,10 +102,10 @@
       this.source = source;
     }
 
-    Binding<T> createBinding(ContainerImpl container) {
+    BindingImpl<T> createBinding(ContainerImpl container) {
       Key<T> key = Key.get(type, annotationStrategy);
       ConstantFactory<T> factory = new ConstantFactory<T>(value);
-      return Binding.newInstance(container, key, source, factory);
+      return BindingImpl.newInstance(container, key, source, factory);
     }
   }
 }
diff --git a/src/com/google/inject/ContainerImpl.java b/src/com/google/inject/ContainerImpl.java
index a0c9542..2888e95 100644
--- a/src/com/google/inject/ContainerImpl.java
+++ b/src/com/google/inject/ContainerImpl.java
@@ -82,7 +82,7 @@
       = new PrimitiveConverters();
 
   final ConstructionProxyFactory constructionProxyFactory;
-  final Map<Key<?>, Binding<?>> bindings;
+  final Map<Key<?>, BindingImpl<?>> bindings;
   final BindingsMultimap bindingsMultimap = new BindingsMultimap();
   final Map<Class<? extends Annotation>, Scope> scopes;
 
@@ -90,7 +90,7 @@
   Object defaultSource = "[unknown source]";
 
   ContainerImpl(ConstructionProxyFactory constructionProxyFactory,
-      Map<Key<?>, Binding<?>> bindings,
+      Map<Key<?>, BindingImpl<?>> bindings,
       Map<Class<? extends Annotation>, Scope> scopes) {
     this.constructionProxyFactory = constructionProxyFactory;
     this.bindings = bindings;
@@ -101,18 +101,19 @@
    * Indexes bindings by type.
    */
   void index() {
-    for (Binding<?> binding : bindings.values()) {
+    for (BindingImpl<?> binding : bindings.values()) {
       index(binding);
     }
   }
 
-  <T> void index(Binding<T> binding) {
+  <T> void index(BindingImpl<T> binding) {
     bindingsMultimap.put(binding.getKey().getType(), binding);
   }
 
   // not test-covered
   public <T> List<Binding<T>> findBindingsByType(TypeLiteral<T> type) {
-    return bindingsMultimap.getAll(type);
+    return Collections.<Binding<T>>unmodifiableList(
+        bindingsMultimap.getAll(type));
   }
 
   // not test-covered
@@ -152,7 +153,7 @@
     // TODO: Clean up unchecked type warnings.
 
     // Do we have a factory for the specified type and name?
-    Binding<T> binding = getBinding(key);
+    BindingImpl<T> binding = getBinding(key);
     if (binding != null) {
       return binding.getInternalFactory();
     }
@@ -188,7 +189,7 @@
     Class<?> primitiveCounterpart
         = PRIMITIVE_COUNTERPARTS.get(rawType);
     if (primitiveCounterpart != null) {
-      Binding<?> counterpartBinding
+      BindingImpl<?> counterpartBinding
           = getBinding(key.ofType(primitiveCounterpart));
       if (counterpartBinding != null) {
         return (InternalFactory<? extends T>)
@@ -198,7 +199,7 @@
 
     // Can we convert from a String constant?
     Key<String> stringKey = key.ofType(String.class);
-    Binding<String> stringBinding = getBinding(stringKey);
+    BindingImpl<String> stringBinding = getBinding(stringKey);
     if (stringBinding != null && stringBinding.isConstant()) {
       // We don't need do pass in an InternalContext because we know this is
       // a ConstantFactory which will not use it.
@@ -360,19 +361,18 @@
     }
   }
 
-  Map<Key<?>, Binding<?>> internalBindings() {
+  Map<Key<?>, BindingImpl<?>> internalBindings() {
     return bindings;
   }
 
   // not test-covered
   public Map<Key<?>, Binding<?>> getBindings() {
-    return Collections.unmodifiableMap(bindings);
+    return Collections.<Key<?>, Binding<?>>unmodifiableMap(bindings);
   }
 
-  // TODO: try to get rid of the warning
   @SuppressWarnings("unchecked")
-  public <T> Binding<T> getBinding(Key<T> key) {
-    return (Binding<T>) bindings.get(key);
+  public <T> BindingImpl<T> getBinding(Key<T> key) {
+    return (BindingImpl<T>) bindings.get(key);
   }
 
   interface InjectorFactory<M extends Member & AnnotatedElement> {
@@ -385,28 +385,28 @@
   }
 
   private static class BindingsMultimap {
-    private final Map<TypeLiteral<?>, List<? extends Binding<?>>> map
-        = new HashMap<TypeLiteral<?>, List<? extends Binding<?>>>();
+    private final Map<TypeLiteral<?>, List<? extends BindingImpl<?>>> map
+        = new HashMap<TypeLiteral<?>, List<? extends BindingImpl<?>>>();
 
-    public <T> void put(TypeLiteral<T> type, Binding<T> binding) {
-      List<Binding<T>> bindingsForThisType = getFromMap(type);
+    public <T> void put(TypeLiteral<T> type, BindingImpl<T> binding) {
+      List<BindingImpl<T>> bindingsForThisType = getFromMap(type);
       if (bindingsForThisType == null) {
-        bindingsForThisType = new ArrayList<Binding<T>>();
+        bindingsForThisType = new ArrayList<BindingImpl<T>>();
         // We only put matching entries into the map
         map.put(type, bindingsForThisType);
       }
       bindingsForThisType.add(binding);
     }
 
-    public <T> List<Binding<T>> getAll(TypeLiteral<T> type) {
-      List<Binding<T>> list = getFromMap(type);
-      return list == null ? Collections.<Binding<T>>emptyList() : list;
+    public <T> List<BindingImpl<T>> getAll(TypeLiteral<T> type) {
+      List<BindingImpl<T>> list = getFromMap(type);
+      return list == null ? Collections.<BindingImpl<T>>emptyList() : list;
     }
 
     // safe because we only put matching entries into the map
     @SuppressWarnings("unchecked")
-    private <T> List<Binding<T>> getFromMap(TypeLiteral<T> type) {
-      return (List<Binding<T>>) map.get(type);
+    private <T> List<BindingImpl<T>> getFromMap(TypeLiteral<T> type) {
+      return (List<BindingImpl<T>>) map.get(type);
     }
   }
 
diff --git a/src/com/google/inject/tools/jmx/Manager.java b/src/com/google/inject/tools/jmx/Manager.java
index 7d1c5fd..9b24b35 100644
--- a/src/com/google/inject/tools/jmx/Manager.java
+++ b/src/com/google/inject/tools/jmx/Manager.java
@@ -16,11 +16,11 @@
 
 package com.google.inject.tools.jmx;
 
-import com.google.inject.Binding;
 import com.google.inject.Container;
 import com.google.inject.Guice;
 import com.google.inject.Key;
 import com.google.inject.Module;
+import com.google.inject.Binding;
 import java.lang.annotation.Annotation;
 import java.lang.management.ManagementFactory;
 import javax.management.MBeanServer;
diff --git a/test/com/google/inject/ReflectionTest.java b/test/com/google/inject/ReflectionTest.java
index 75b6712..e7f4a79 100644
--- a/test/com/google/inject/ReflectionTest.java
+++ b/test/com/google/inject/ReflectionTest.java
@@ -37,7 +37,6 @@
     assertSame(foo, fooBinding.getProvider().get());
     assertNotNull(fooBinding.getSource());
     assertEquals(Key.get(Foo.class), fooBinding.getKey());
-    assertTrue(fooBinding.isConstant());
   }
 
   public void testConstantBinding() throws CreationException {
@@ -48,7 +47,6 @@
     assertEquals(5, i.getProvider().get());
     assertNotNull(i.getSource());
     assertEquals(Key.get(int.class, I.class), i.getKey());
-    assertTrue(i.isConstant());
   }
 
   public void testLinkedBinding() throws CreationException {
@@ -61,7 +59,6 @@
     assertSame(bar, fooBinding.getProvider().get());
     assertNotNull(fooBinding.getSource());
     assertEquals(Key.get(Foo.class), fooBinding.getKey());
-    assertTrue(fooBinding.isConstant());
   }
 
   static class Foo {}