In progress [Issue 125] Support for custom options.

Code cleanup. Adding more tests.
diff --git a/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_fieldFrom_Test.java b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_fieldFrom_Test.java
new file mode 100644
index 0000000..81e38e6
--- /dev/null
+++ b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_fieldFrom_Test.java
@@ -0,0 +1,62 @@
+/*
+ * Copyright (c) 2011 Google Inc.
+ *
+ * All rights reserved. This program and the accompanying materials are made available under the terms of the Eclipse
+ * Public License v1.0 which accompanies this distribution, and is available at
+ *
+ * http://www.eclipse.org/legal/epl-v10.html
+ */
+package com.google.eclipse.protobuf.util;
+
+import static com.google.eclipse.protobuf.junit.find.FieldOptionFinder.findFieldOption;
+import static com.google.eclipse.protobuf.junit.find.Name.name;
+import static com.google.eclipse.protobuf.junit.find.Root.in;
+import static org.hamcrest.core.IsEqual.equalTo;
+import static org.junit.Assert.assertThat;
+
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+
+import com.google.eclipse.protobuf.junit.core.XtextRule;
+import com.google.eclipse.protobuf.junit.util.MultiLineTextBuilder;
+import com.google.eclipse.protobuf.protobuf.CustomFieldOption;
+import com.google.eclipse.protobuf.protobuf.Property;
+import com.google.eclipse.protobuf.protobuf.Protobuf;
+
+/**
+ * Tests for <code>{@link FieldOptions#fieldFrom(CustomFieldOption)}</code>.
+ * 
+ * alruiz@google.com (Alex Ruiz)
+ */
+public class FieldOptions_fieldFrom_Test {
+
+  @Rule public XtextRule xtext = XtextRule.integrationTestSetup();
+
+  private FieldOptions fieldOptions;
+
+  @Before public void setUp() {
+    fieldOptions = xtext.getInstanceOf(FieldOptions.class);
+  }
+  
+  @Test public void should_return_property_field() {
+    MultiLineTextBuilder proto = new MultiLineTextBuilder();
+    proto.append("import 'google/protobuf/descriptor.proto';         ")
+         .append("                                                   ")
+         .append("message Custom {                                   ")
+         .append("  optional int32 count = 1;                        ")
+         .append("}                                                  ")
+         .append("                                                   ")
+         .append("extend google.protobuf.FieldOptions {              ")
+         .append("  optional Custom custom = 1000;                   ")
+         .append("}                                                  ")
+         .append("                                                   ")
+         .append("message Person {                                   ")
+         .append("  optional boolean active = 1 [(custom).count = 6];")
+         .append("}                                                  ");
+    Protobuf root = xtext.parseText(proto);
+    CustomFieldOption option = (CustomFieldOption) findFieldOption(name("custom"), in(root));
+    Property p = fieldOptions.fieldFrom(option);
+    assertThat(p.getName(), equalTo("count"));
+  }
+}
diff --git a/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_nameOf_Test.java b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_nameOf_Test.java
index c8181e9..6d97e35 100644
--- a/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_nameOf_Test.java
+++ b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_nameOf_Test.java
@@ -48,7 +48,7 @@
 
   @Test public void should_return_name_of_custom_field_option() {
     MultiLineTextBuilder proto = new MultiLineTextBuilder();
-    proto.append("import \"google/protobuf/descriptor.proto\";         ")
+    proto.append("import 'google/protobuf/descriptor.proto';         ")
          .append("                                                     ")
          .append("extend google.protobuf.FieldOptions {                ")
          .append("  optional string encoding = 1000;                   ")
diff --git a/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_propertyFrom_Test.java b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_propertyFrom_Test.java
index 8a86499..7d3e768 100644
--- a/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_propertyFrom_Test.java
+++ b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/FieldOptions_propertyFrom_Test.java
@@ -48,7 +48,7 @@
 
   @Test public void should_return_property_of_custom_field_option() {
     MultiLineTextBuilder proto = new MultiLineTextBuilder();
-    proto.append("import \"google/protobuf/descriptor.proto\";         ")
+    proto.append("import 'google/protobuf/descriptor.proto';           ")
          .append("                                                     ")
          .append("extend google.protobuf.FieldOptions {                ")
          .append("  optional string encoding = 1000;                   ")
diff --git a/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/Options_fieldFrom_Test.java b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/Options_fieldFrom_Test.java
new file mode 100644
index 0000000..a8cc57f
--- /dev/null
+++ b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/Options_fieldFrom_Test.java
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2011 Google Inc.
+ *
+ * All rights reserved. This program and the accompanying materials are made available under the terms of the Eclipse
+ * Public License v1.0 which accompanies this distribution, and is available at
+ *
+ * http://www.eclipse.org/legal/epl-v10.html
+ */
+package com.google.eclipse.protobuf.util;
+
+import static com.google.eclipse.protobuf.junit.find.Name.name;
+import static com.google.eclipse.protobuf.junit.find.OptionFinder.findOption;
+import static com.google.eclipse.protobuf.junit.find.Root.in;
+import static org.hamcrest.core.IsEqual.equalTo;
+import static org.junit.Assert.assertThat;
+
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+
+import com.google.eclipse.protobuf.junit.core.XtextRule;
+import com.google.eclipse.protobuf.junit.util.MultiLineTextBuilder;
+import com.google.eclipse.protobuf.protobuf.CustomOption;
+import com.google.eclipse.protobuf.protobuf.Property;
+import com.google.eclipse.protobuf.protobuf.Protobuf;
+
+/**
+ * Tests for <code>{@link Options#fieldFrom(CustomOption)}</code>.
+ * 
+ * alruiz@google.com (Alex Ruiz)
+ */
+public class Options_fieldFrom_Test {
+
+  @Rule public XtextRule xtext = XtextRule.integrationTestSetup();
+
+  private Options options;
+
+  @Before public void setUp() {
+    options = xtext.getInstanceOf(Options.class);
+  }
+  
+  @Test public void should_return_property_field() {
+    MultiLineTextBuilder proto = new MultiLineTextBuilder();
+    proto.append("import 'google/protobuf/descriptor.proto';")
+         .append("                                          ")
+         .append("message Custom {                          ")
+         .append("  optional int32 count = 1;               ")
+         .append("}                                         ")
+         .append("                                          ")
+         .append("extend google.protobuf.FileOptions {      ")
+         .append("  optional Custom custom = 1000;          ")
+         .append("}                                         ")
+         .append("                                          ")
+         .append("option (custom).count = 6;");
+    Protobuf root = xtext.parseText(proto);
+    CustomOption option = (CustomOption) findOption(name("custom"), in(root));
+    Property p = options.fieldFrom(option);
+    assertThat(p.getName(), equalTo("count"));
+  }
+}
diff --git a/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/Options_propertyFrom_Test.java b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/Options_propertyFrom_Test.java
new file mode 100644
index 0000000..3243aaf
--- /dev/null
+++ b/com.google.eclipse.protobuf.integration.test/src/com/google/eclipse/protobuf/util/Options_propertyFrom_Test.java
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2011 Google Inc.
+ *
+ * All rights reserved. This program and the accompanying materials are made available under the terms of the Eclipse
+ * Public License v1.0 which accompanies this distribution, and is available at
+ *
+ * http://www.eclipse.org/legal/epl-v10.html
+ */
+package com.google.eclipse.protobuf.util;
+
+import static com.google.eclipse.protobuf.junit.find.Name.name;
+import static com.google.eclipse.protobuf.junit.find.OptionFinder.findOption;
+import static com.google.eclipse.protobuf.junit.find.Root.in;
+import static org.hamcrest.core.IsEqual.equalTo;
+import static org.junit.Assert.assertThat;
+
+import org.junit.*;
+
+import com.google.eclipse.protobuf.junit.core.XtextRule;
+import com.google.eclipse.protobuf.junit.util.MultiLineTextBuilder;
+import com.google.eclipse.protobuf.protobuf.*;
+
+/**
+ * Tests for <code>{@link Options#propertyFrom(Option)}</code>.
+ *
+ * @author alruiz@google.com (Alex Ruiz)
+ */
+public class Options_propertyFrom_Test {
+
+  @Rule public XtextRule xtext = XtextRule.integrationTestSetup();
+
+  private Options options;
+
+  @Before public void setUp() {
+    options = xtext.getInstanceOf(Options.class);
+  }
+
+  @Test public void should_return_property_of_native_option() {
+    MultiLineTextBuilder proto = new MultiLineTextBuilder();
+    proto.append("option java_package = 'com.google.eclipse.protobuf.tests';");
+    Protobuf root = xtext.parseText(proto);
+    Option option = findOption(name("java_package"), in(root));
+    Property p = options.propertyFrom(option);
+    assertThat(p.getName(), equalTo("java_package"));
+  }
+
+  @Test public void should_return_property_of_custom_option() {
+    MultiLineTextBuilder proto = new MultiLineTextBuilder();
+    proto.append("import 'google/protobuf/descriptor.proto';")
+         .append("                                          ")
+         .append("extend google.protobuf.FileOptions {      ")
+         .append("  optional string encoding = 1000;        ")
+         .append("}                                         ")
+         .append("                                          ")
+         .append("option (encoding) = 'UTF-8';              ");
+    Protobuf root = xtext.parseText(proto);
+    Option option = findOption(name("encoding"), in(root));
+    Property p = options.propertyFrom(option);
+    assertThat(p.getName(), equalTo("encoding"));
+  }
+}
diff --git a/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/CustomOptionProperties.java b/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/CustomOptionProperties.java
index 30d8818..ba8479f 100644
--- a/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/CustomOptionProperties.java
+++ b/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/CustomOptionProperties.java
@@ -40,16 +40,16 @@
     Protobuf root = finder.rootOf(option);
     if (root == null) return emptyList();
     List<Property> properties = new ArrayList<Property>();
-    properties.addAll(localProperties(root, type));
-    properties.addAll(importedProperties(root, type));
+    properties.addAll(local(root, type));
+    properties.addAll(imported(root, type));
     return unmodifiableList(properties);
   }
 
-  private Collection<Property> localProperties(Protobuf root, OptionType type) {
-    return localProperties(root, type, 0);
+  private Collection<Property> local(Protobuf root, OptionType type) {
+    return local(root, type, 0);
   }
 
-  private Collection<Property> localProperties(EObject root, OptionType optionType, int level) {
+  private Collection<Property> local(EObject root, OptionType optionType, int level) {
     List<Property> properties = new ArrayList<Property>();
     for (EObject element : root.eContents()) {
       if (options.isExtendingOptionMessage(element, optionType)) {
@@ -60,20 +60,20 @@
         }
       }
       if (element instanceof Message) {
-        properties.addAll(localProperties(element, optionType, level + 1));
+        properties.addAll(local(element, optionType, level + 1));
       }
     }
     return unmodifiableList(properties);
   }
 
-  private Collection<Property> importedProperties(Protobuf root, OptionType optionType) {
+  private Collection<Property> imported(Protobuf root, OptionType optionType) {
     List<Import> allImports = finder.importsIn(root);
     if (allImports.isEmpty()) return emptyList();
     ResourceSet resourceSet = root.eResource().getResourceSet();
-    return importedProperties(allImports, finder.packageOf(root), resourceSet, optionType);
+    return imported(allImports, finder.packageOf(root), resourceSet, optionType);
   }
 
-  private Collection<Property> importedProperties(List<Import> allImports, Package aPackage,
+  private Collection<Property> imported(List<Import> allImports, Package aPackage,
       ResourceSet resourceSet, OptionType optionType) {
     List<Property> properties = new ArrayList<Property>();
     for (Import anImport : allImports) {
@@ -81,22 +81,22 @@
       Resource importedResource = resources.importedResource(anImport, resourceSet);
       Protobuf importedRoot = finder.rootOf(importedResource);
       if (importedRoot != null) {
-        properties.addAll(publicImportedProperties(importedRoot, optionType));
+        properties.addAll(publicImported(importedRoot, optionType));
         if (arePackagesRelated(aPackage, importedRoot)) {
-          properties.addAll(localProperties(importedRoot, optionType));
+          properties.addAll(local(importedRoot, optionType));
           continue;
         }
       }
-      properties.addAll(localProperties(importedResource, optionType));
+      properties.addAll(local(importedResource, optionType));
     }
     return unmodifiableList(properties);
   }
 
-  private Collection<Property> publicImportedProperties(Protobuf root, OptionType optionType) {
+  private Collection<Property> publicImported(Protobuf root, OptionType optionType) {
     List<Import> allImports = finder.publicImportsIn(root);
     if (allImports.isEmpty()) return emptyList();
     ResourceSet resourceSet = root.eResource().getResourceSet();
-    return importedProperties(allImports, finder.packageOf(root), resourceSet, optionType);
+    return imported(allImports, finder.packageOf(root), resourceSet, optionType);
   }
 
   private boolean arePackagesRelated(Package aPackage, EObject root) {
@@ -104,7 +104,7 @@
     return packages.areRelated(aPackage, p);
   }
 
-  private Collection<Property> localProperties(Resource resource, OptionType optionType) {
+  private Collection<Property> local(Resource resource, OptionType optionType) {
     List<Property> properties = new ArrayList<Property>();
     TreeIterator<Object> contents = getAllContents(resource, true);
     while (contents.hasNext()) {
diff --git a/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/ProtobufProposalProvider.java b/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/ProtobufProposalProvider.java
index 2948337..740b443 100644
--- a/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/ProtobufProposalProvider.java
+++ b/com.google.eclipse.protobuf.ui/src/com/google/eclipse/protobuf/ui/contentassist/ProtobufProposalProvider.java
@@ -438,7 +438,7 @@
       ICompletionProposalAcceptor acceptor) {
     if (!(model instanceof CustomOption)) return;
     CustomOption option = (CustomOption) model;
-    Property property = options.propertyFieldFrom(option);
+    Property property = options.fieldFrom(option);
     if (property == null) property = options.propertyFrom(option);
     if (property == null) return;
     if (proposePrimitiveValues(property, context, acceptor)) return;
diff --git a/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/scoping/ProtobufScopeProvider.java b/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/scoping/ProtobufScopeProvider.java
index bb6691d..4b2a06c 100644
--- a/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/scoping/ProtobufScopeProvider.java
+++ b/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/scoping/ProtobufScopeProvider.java
@@ -74,7 +74,7 @@
     }
     if (c instanceof CustomOption) {
       CustomOption option = (CustomOption) c;
-      c = options.propertyFieldFrom(option);
+      c = options.fieldFrom(option);
       if (c == null) c = options.propertyFrom(option);
     }
     if (c instanceof NativeFieldOption) {
@@ -84,7 +84,7 @@
     }
     if (c instanceof CustomFieldOption) {
       CustomFieldOption option = (CustomFieldOption) c;
-      c = fieldOptions.propertyFieldFrom(option);
+      c = fieldOptions.fieldFrom(option);
       if (c == null) c = fieldOptions.propertyFrom(option);
     }
     if (c instanceof Property) {
diff --git a/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/FieldOptions.java b/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/FieldOptions.java
index 21e6f48..5291ee4 100644
--- a/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/FieldOptions.java
+++ b/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/FieldOptions.java
@@ -63,17 +63,17 @@
   }
 
   /**
-   * Returns the <code>{@link Property}</code> field the given <code>{@link CustomFieldOption}</code> is referring to. 
-   * In the following example
+   * Returns the field of the <code>{@link Property}</code> the given <code>{@link CustomFieldOption}</code> is 
+   * referring to. In the following example
    * <pre>
    * [(myFieldOption).field = true]
    * </pre>
    * this method will return the <code>{@link Property}</code> "field" is pointing to.
    * @param option the given {@code FieldOption}.
-   * @return the {@code Property} the given {@code CustomFieldOption} is referring to, or {@code null} if it cannot be
-   * found.
+   * @return the field of the {@code Property} the given {@code CustomFieldOption} is referring to, or {@code null} if 
+   * one cannot be found.
    */
-  public Property propertyFieldFrom(CustomFieldOption option) {
+  public Property fieldFrom(CustomFieldOption option) {
     SimplePropertyRef ref = option.getPropertyField();
     return (ref == null) ? null : ref.getProperty();
   }
diff --git a/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/Options.java b/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/Options.java
index 67d54bc..f92ae92 100644
--- a/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/Options.java
+++ b/com.google.eclipse.protobuf/src/com/google/eclipse/protobuf/util/Options.java
@@ -22,19 +22,6 @@
 public class Options {
 
   /**
-   * Indicates whether the given option is a file-level option.
-   * @param option the option to verify.
-   * @return {@code true} if the given option is a file-level option, {@code false} otherwise.
-   */
-  public boolean isFileOption(Option option) {
-    return isOptionContainerInstanceOf(option, Protobuf.class);
-  }
-
-  private boolean isOptionContainerInstanceOf(Option option, Class<? extends EObject> type) {
-    return type.isInstance(option.eContainer());
-  }
-
-  /**
    * Returns the <code>{@link Property}</code> the given <code>{@link Option}</code> is referring to. In the
    * following example
    * <pre>
@@ -51,17 +38,17 @@
   }
 
   /**
-   * Returns the <code>{@link Property}</code> field the given <code>{@link CustomOption}</code> is referring to. In the
-   * following example
+   * Returns the field of the <code>{@link Property}</code> the given <code>{@link CustomOption}</code> is referring to. 
+   * In the following example
    * <pre>
    * option (myOption).field = true;
    * </pre>
    * this method will return the <code>{@link Property}</code> "field" is pointing to.
    * @param option the given {@code Option}.
-   * @return the {@code Property} the given {@code CustomOption} is referring to, or {@code null} if it cannot be
-   * found.
+   * @return the field of the {@code Property} the given {@code CustomOption} is referring to, or {@code null} if one 
+   * cannot be found.
    */
-  public Property propertyFieldFrom(CustomOption option) {
+  public Property fieldFrom(CustomOption option) {
     SimplePropertyRef ref = option.getPropertyField();
     return (ref == null) ? null : ref.getProperty();
   }