Add examples to create scalars that match custom regular expression
diff --git a/src/changes/changes.xml b/src/changes/changes.xml
index 9d963a1..da2849b 100644
--- a/src/changes/changes.xml
+++ b/src/changes/changes.xml
@@ -7,6 +7,10 @@
</properties>
<body>
<release version="1.7" date="in Mercurial" description="development">
+ <action dev="py4fun" type="update" issue="75" due-to="jon.p.hermes">
+ Add examples to create scalars that match custom regular expression:
+ CustomImplicitResolverTest, CustomBeanResolverTest (2010-08-03)
+ </action>
<action dev="py4fun" type="fix" issue="74" due-to="Kevin Menard">
Do not use redundant tags for arrays which are JavaBean properties. (2010-07-21)
</action>
diff --git a/src/test/java/examples/CustomBeanResolverTest.java b/src/test/java/examples/CustomBeanResolverTest.java
new file mode 100644
index 0000000..ecc452b
--- /dev/null
+++ b/src/test/java/examples/CustomBeanResolverTest.java
@@ -0,0 +1,85 @@
+/**
+ * Copyright (c) 2008-2010, http://code.google.com/p/snakeyaml/
+ *
+ * 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 examples;
+
+import java.math.BigDecimal;
+import java.util.regex.Pattern;
+
+import junit.framework.TestCase;
+
+import org.yaml.snakeyaml.Loader;
+import org.yaml.snakeyaml.Yaml;
+import org.yaml.snakeyaml.constructor.Constructor;
+import org.yaml.snakeyaml.nodes.Node;
+import org.yaml.snakeyaml.nodes.NodeId;
+import org.yaml.snakeyaml.nodes.ScalarNode;
+
+/**
+ * http://code.google.com/p/snakeyaml/issues/detail?id=75
+ */
+public class CustomBeanResolverTest extends TestCase {
+ private final Pattern CUSTOM_PATTERN = Pattern.compile("\\d+%");
+
+ public void testOnlyBigDecimal() {
+ Yaml yaml = new Yaml(new Loader(new BigBeanConstructor()));
+ Foo foo = (Foo) yaml.load("bar: 50\nbaz: 35%\nbas: 1250");
+ assertEquals(50.0, foo.bar);
+ assertEquals("0.35", foo.baz.toString());
+ assertEquals("1250", foo.bas);
+ }
+
+ public void testPrimitive() {
+ Yaml yaml = new Yaml(new Loader(new BigBeanConstructor()));
+ Foo foo = (Foo) yaml.load("bar: 50%\nbaz: 35%\nbas: 1250%\nbaw: 35");
+ assertEquals(0.5, foo.bar);
+ assertEquals("0.35", foo.baz.toString());
+ assertEquals("1250%", foo.bas);
+ assertEquals("35", foo.baw.toString());
+ }
+
+ class BigBeanConstructor extends Constructor {
+ public BigBeanConstructor() {
+ super(Foo.class);
+ yamlClassConstructors.put(NodeId.scalar, new ConstructBig());
+ }
+
+ private class ConstructBig extends ConstructScalar {
+ public Object construct(Node node) {
+ if (node.getType().equals(BigDecimal.class)) {
+ String val = (String) constructScalar((ScalarNode) node);
+ if (CUSTOM_PATTERN.matcher(val).matches()) {
+ return new BigDecimal(val.substring(0, val.length() - 1))
+ .divide(new BigDecimal(100));
+ }
+ } else if (node.getType().isAssignableFrom(double.class)) {
+ String val = (String) constructScalar((ScalarNode) node);
+ if (CUSTOM_PATTERN.matcher(val).matches()) {
+ return new Double(val.substring(0, val.length() - 1)) / 100;
+ }
+ }
+ return super.construct(node);
+ }
+ }
+ }
+
+ public static class Foo {
+ public double bar = 0;
+ public BigDecimal baz;
+ public BigDecimal baw;
+ public String bas;
+ }
+}
diff --git a/src/test/java/examples/CustomImplicitResolverTest.java b/src/test/java/examples/CustomImplicitResolverTest.java
new file mode 100644
index 0000000..34aa44d
--- /dev/null
+++ b/src/test/java/examples/CustomImplicitResolverTest.java
@@ -0,0 +1,74 @@
+/**
+ * Copyright (c) 2008-2010, http://code.google.com/p/snakeyaml/
+ *
+ * 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 examples;
+
+import java.math.BigDecimal;
+import java.util.Map;
+import java.util.regex.Pattern;
+
+import junit.framework.TestCase;
+
+import org.yaml.snakeyaml.Loader;
+import org.yaml.snakeyaml.Yaml;
+import org.yaml.snakeyaml.constructor.AbstractConstruct;
+import org.yaml.snakeyaml.constructor.SafeConstructor;
+import org.yaml.snakeyaml.nodes.Node;
+import org.yaml.snakeyaml.nodes.ScalarNode;
+import org.yaml.snakeyaml.nodes.Tag;
+
+/**
+ * Use custom implicit resolver when the runtime class is not defined.
+ * http://code.google.com/p/snakeyaml/issues/detail?id=75
+ */
+public class CustomImplicitResolverTest extends TestCase {
+ private final Tag CUSTOM_TAG = new Tag("!BigDecimalDividedBy100");
+ private final Pattern CUSTOM_PATTERN = Pattern.compile("\\d+%");
+
+ @SuppressWarnings("unchecked")
+ public void testImplicit() {
+ Yaml yaml = new Yaml(new Loader(new BigConstructor()));
+ yaml.addImplicitResolver(CUSTOM_TAG, CUSTOM_PATTERN, "-0123456789");
+ Map<String, Object> obj = (Map<String, Object>) yaml.load("bar: 50%");
+ assertEquals("0.5", obj.get("bar").toString());
+ assertEquals(BigDecimal.class, obj.get("bar").getClass());
+ }
+
+ public void testImplicitFailure() {
+ Yaml yaml = new Yaml(new Loader(new BigConstructor()));
+ yaml.addImplicitResolver(CUSTOM_TAG, Pattern.compile("\\d+%"), "-0123456789");
+ try {
+ yaml.load("bar: !!float 50%");
+ fail("Both implicit and explicit are present.");
+ } catch (NumberFormatException e) {
+ assertEquals("For input string: \"50%\"", e.getMessage());
+ }
+ }
+
+ class BigConstructor extends SafeConstructor {
+ public BigConstructor() {
+ this.yamlConstructors.put(CUSTOM_TAG, new ConstructBig());
+ }
+
+ private class ConstructBig extends AbstractConstruct {
+ public Object construct(Node node) {
+ String val = (String) constructScalar((ScalarNode) node);
+ return new BigDecimal(val.substring(0, val.length() - 1))
+ .divide(new BigDecimal(100));
+ }
+ }
+ }
+}