[jboss-svn-commits] JBL Code SVN: r33568 - in labs/jbossrules/trunk: drools-decisiontables/src/test/java/org/drools/decisiontable/parser and 3 other directories.

jboss-svn-commits at lists.jboss.org jboss-svn-commits at lists.jboss.org
Mon Jun 21 09:31:16 EDT 2010


Author: ggear
Date: 2010-06-21 09:31:16 -0400 (Mon, 21 Jun 2010)
New Revision: 33568

Modified:
   labs/jbossrules/trunk/drools-decisiontables/src/main/java/org/drools/decisiontable/parser/LhsBuilder.java
   labs/jbossrules/trunk/drools-decisiontables/src/test/java/org/drools/decisiontable/parser/LhsBuilderTest.java
   labs/jbossrules/trunk/drools-docs/drools-docs-expert/src/main/docbook/en-US/Chapter-Authoring/Section-Decision_Tables.xml
   labs/jbossrules/trunk/drools-templates/src/main/java/org/drools/template/model/SnippetBuilder.java
   labs/jbossrules/trunk/drools-templates/src/test/java/org/drools/template/model/SnippetBuilderTest.java
Log:
JBRULES-2455

Modified: labs/jbossrules/trunk/drools-decisiontables/src/main/java/org/drools/decisiontable/parser/LhsBuilder.java
===================================================================
--- labs/jbossrules/trunk/drools-decisiontables/src/main/java/org/drools/decisiontable/parser/LhsBuilder.java	2010-06-21 08:41:48 UTC (rev 33567)
+++ labs/jbossrules/trunk/drools-decisiontables/src/main/java/org/drools/decisiontable/parser/LhsBuilder.java	2010-06-21 13:31:16 UTC (rev 33568)
@@ -61,9 +61,9 @@
             constraints.put( key,
                              content );            
         } else if (fieldType == FieldType.SINGLE_FIELD) {
-            constraints.put( key, content + " == \"$param\"" );
+            constraints.put( key, content + " == \"" + SnippetBuilder.PARAM_STRING + "\"" );
         } else if (fieldType == FieldType.OPERATOR_FIELD) {
-            constraints.put( key, content + " \"$param\"" );
+            constraints.put( key, content + " \"" + SnippetBuilder.PARAM_STRING + "\"" );
         }
         
     }
@@ -133,14 +133,17 @@
      * age 
      * age <
      * age == $param
+     * age == $1 || age == $2
+     * forall{age < $}{,}
      * 
      * etc. as we treat them all differently.
      */
-    public FieldType calcFieldType(String content) {
-        if (content.indexOf( "$param" ) != -1 || content.indexOf( "$1" ) != -1 ) {
-            return FieldType.NORMAL_FIELD;
-        }
-        for ( String op : operators ) {
+	public FieldType calcFieldType(String content) {
+		if (!SnippetBuilder.getType(content).equals(
+				SnippetBuilder.SnippetType.SINGLE)) {
+			return FieldType.NORMAL_FIELD;
+		}
+       for ( String op : operators ) {
             if (content.endsWith( op )) {
                 return FieldType.OPERATOR_FIELD;
             }            

Modified: labs/jbossrules/trunk/drools-decisiontables/src/test/java/org/drools/decisiontable/parser/LhsBuilderTest.java
===================================================================
--- labs/jbossrules/trunk/drools-decisiontables/src/test/java/org/drools/decisiontable/parser/LhsBuilderTest.java	2010-06-21 08:41:48 UTC (rev 33567)
+++ labs/jbossrules/trunk/drools-decisiontables/src/test/java/org/drools/decisiontable/parser/LhsBuilderTest.java	2010-06-21 13:31:16 UTC (rev 33568)
@@ -47,14 +47,90 @@
         
         assertEquals("Foo(bar == 42)\neval(true)", builder.getResult());
     }
+ 
+	public void testForAllAndFucntion() {
+		LhsBuilder builder = new LhsBuilder("");
+		builder.addTemplate(1, "forall(&&){Foo(bar != $)}");
+		builder.addCellValue(1, "42,43");
+		assertEquals("Foo(bar != 42) && Foo(bar != 43)", builder.getResult());
+	}
     
+	public void testForAllOr() {
+		LhsBuilder builder = new LhsBuilder("Person");
+		builder.addTemplate(1, "forall(||){age < $}");
+		builder.addCellValue(1, "42");
+		assertEquals("Person(age < 42)", builder.getResult());
+	}
+
+	public void testForAllOrPrefix() {
+		LhsBuilder builder = new LhsBuilder("Person");
+		builder.addTemplate(1, "age < 10 && forall(||){age < $}");
+		builder.addCellValue(1, "42");
+		assertEquals("Person(age < 10 && age < 42)", builder.getResult());
+	}
+	
+	public void testForAllOrCSV() {
+		LhsBuilder builder = new LhsBuilder("Person");
+		builder.addTemplate(1, "forall(||){age < $}");
+		builder.addCellValue(1, "42, 43, 44");
+		assertEquals("Person(age < 42 || age < 43 || age < 44)", builder
+				.getResult());
+	}
+
+	public void testForAllAnd() {
+		LhsBuilder builder = new LhsBuilder("Person");
+		builder.addTemplate(1, "forall(&&){age < $}");
+		builder.addCellValue(1, "42");
+		assertEquals("Person(age < 42)", builder.getResult());
+	}
+
+	public void testForAllAndCSV() {
+		LhsBuilder builder = new LhsBuilder("Person");
+		builder.addTemplate(1, "forall(&&){age < $}");
+		builder.addCellValue(1, "42, 43, 44");
+		assertEquals("Person(age < 42 && age < 43 && age < 44)", builder
+				.getResult());
+	}
+
+	public void testForAllAndForAllOrCSVMultiple() {
+		LhsBuilder builder = new LhsBuilder("Person");
+		builder.addTemplate(1, "forall(&&){age < $ || age == $}");
+		builder.addCellValue(1, "42, 43, 44");
+		assertEquals(
+				"Person(age < 42 || age == 42 && age < 43 || age == 43 && age < 44 || age == 44)",
+				builder.getResult());
+	}
+
+	public void testForAllsAndForAllOrCSVMultiple() {
+		LhsBuilder builder = new LhsBuilder("Person");
+		builder.addTemplate(1, "forall(&&){age < $ || age == $} && forall(&&){age < $ || age == $}");
+		builder.addCellValue(1, "42, 43, 44");
+		assertEquals(
+				"Person(age < 42 || age == 42 && age < 43 || age == 43 && age < 44 || age == 44 && age < 42 || age == 42 && age < 43 || age == 43 && age < 44 || age == 44)",
+				builder.getResult());
+	}
+	
     public void testIdentifyFieldTypes() {
         LhsBuilder builder = new LhsBuilder("");
         assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("age"));
         assertEquals(FieldType.OPERATOR_FIELD, builder.calcFieldType("age <"));
         assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("age < $param"));
-        
-        
+        assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("forall(||){age < $}"));
+        assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("forall(&&){age < $}"));
+        assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("forall(,){age < $}"));
+        assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("forall(){age < $}"));
+        assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("forall(){age < $} && forall(){age == $}"));
+        assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("x && forall(){age < $} && forall(){age == $}"));
+        assertEquals(FieldType.NORMAL_FIELD, builder.calcFieldType("x && forall(){age < $} && forall(){age == $} && y"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("age < $para"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall{||}{age < $}"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall(){}"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall(){age < $"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall(){,"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall({})"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall({}){test})"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall(&&){{}})"));
+        assertEquals(FieldType.SINGLE_FIELD, builder.calcFieldType("forall(&&){{})"));
     }
     
     public void testIdentifyColumnCorrectly() {

Modified: labs/jbossrules/trunk/drools-docs/drools-docs-expert/src/main/docbook/en-US/Chapter-Authoring/Section-Decision_Tables.xml
===================================================================
--- labs/jbossrules/trunk/drools-docs/drools-docs-expert/src/main/docbook/en-US/Chapter-Authoring/Section-Decision_Tables.xml	2010-06-21 08:41:48 UTC (rev 33567)
+++ labs/jbossrules/trunk/drools-docs/drools-docs-expert/src/main/docbook/en-US/Chapter-Authoring/Section-Decision_Tables.xml	2010-06-21 13:31:16 UTC (rev 33568)
@@ -263,9 +263,11 @@
         <para>The <code>$param</code> place holder is used in templates to
         indicate where data form the cell will be interpolated. You can also
         use <code>$1</code> to the same effect. If the cell contains a comma
-        separated list of values. Symbols $1, $2, etc. may be used to indicate which
+        separated list of values, the symbols $1, $2, etc. may be used to indicate which
         positional parameter from the list of values in the cell will be
-        used.</para>
+        used. The <code>forall(DELIMITER){SNIPPET}</code> function can be used
+	to loop over all available comma separated values.
+	</para>
 
         <example>
           <title>Interpolating cell data</title>
@@ -273,8 +275,12 @@
           ] then the result will be [Foo(bar == 42)].</para>
 
           <para>If the template is
-          [Foo(bar &lt; $1, baz == $2)] and the cell is [42,42] then the
-          result will be [Foo(bar &gt; 42, baz ==42)]</para>
+          [Foo(bar &lt; $1, baz == $2)] and the cell is [42,43] then the
+          result will be [Foo(bar &lt; 42, baz ==43)]</para>
+
+          <para>If the template is
+          [forall(&amp;&amp;){Foo(bar != $)}] and the cell is [42,43] then the
+          result will be [Foo(bar != 42) &amp;&amp; Foo(bar != 43)]</para>
         </example>
 
         <para>For conditions: How snippets are rendered depends on the presence

Modified: labs/jbossrules/trunk/drools-templates/src/main/java/org/drools/template/model/SnippetBuilder.java
===================================================================
--- labs/jbossrules/trunk/drools-templates/src/main/java/org/drools/template/model/SnippetBuilder.java	2010-06-21 08:41:48 UTC (rev 33567)
+++ labs/jbossrules/trunk/drools-templates/src/main/java/org/drools/template/model/SnippetBuilder.java	2010-06-21 13:31:16 UTC (rev 33568)
@@ -1,7 +1,9 @@
 package org.drools.template.model;
 
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.List;
+import java.util.Map;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
@@ -36,13 +38,20 @@
  */
 public class SnippetBuilder {
 
-    private static final String PARAM_PREFIX = "$";
+	public enum SnippetType {
+		SINGLE, PARAM, INDEXED, FORALL
+	};
 
-    private static final String PARAM        = SnippetBuilder.PARAM_PREFIX + "param";
+	public static final String PARAM_PREFIX = "$";
+	public static final String PARAM_SUFFIX = "param";
+	public static final String PARAM_STRING = PARAM_PREFIX + PARAM_SUFFIX;
+	public static final String PARAM_FORALL_STRING = "forall";
+	public static final Pattern PARAM_FORALL_PATTERN = Pattern
+			.compile(PARAM_FORALL_STRING + "\\(([^{}]*)\\)\\{([^{}]+)\\}");
 
     private final String        _template;
     
-    private final boolean       single;
+    private final SnippetType   type;
     
     private final Pattern       delimiter;
 
@@ -56,30 +65,65 @@
             throw new RuntimeException( "Script template is null - check for missing script definition." );
         }
         this._template = snippetTemplate;
-        this.single = this._template.indexOf( SnippetBuilder.PARAM_PREFIX + "1" ) < 0;
+        this.type = getType(_template);
         this.delimiter = Pattern.compile( "(.*?[^\\\\])(,|\\z)" );
     }
 
+	public static SnippetType getType(String template) {
+		Matcher forallMatcher = PARAM_FORALL_PATTERN.matcher(template);
+		if (forallMatcher.find())
+			return SnippetType.FORALL;
+		else if (template.indexOf(PARAM_PREFIX + "1") != -1)
+			return SnippetType.INDEXED;
+		else if (template.indexOf(PARAM_STRING) != -1)
+			return SnippetType.PARAM;
+		return SnippetType.SINGLE;
+	}
+    
     /**
      * @param cellValue
      *            The value from the cell to populate the snippet with. If no
      *            place holder exists, will just return the snippet.
      * @return The final snippet.
      */
-    public String build(final String cellValue) {
-        if ( single ) {
-            return buildSingle( cellValue );
-        } else {
-            return buildMulti( cellValue );
-        }
-    }
+	public String build(final String cellValue) {
+		switch (type) {
+		case FORALL:
+			return buildForAll(cellValue);
+		case INDEXED:
+			return buildMulti(cellValue);
+		default:
+			return buildSingle(cellValue);
+		}
+	}
 
+	private String buildForAll(final String cellValue) {
+		final String[] cellVals = split(cellValue);
+		Map<String, String> replacements = new HashMap<String, String>();
+		Matcher forallMatcher = PARAM_FORALL_PATTERN.matcher(_template);
+		while (forallMatcher.find()) {
+			replacements.put(forallMatcher.group(), "");
+			for (int paramNumber = 0; paramNumber < cellVals.length; paramNumber++) {
+				replacements.put(forallMatcher.group(), replacements
+						.get(forallMatcher.group())
+						+ (paramNumber == 0 ? "" : " " + forallMatcher.group(1)
+								+ " ")
+						+ replace(forallMatcher.group(2), PARAM_PREFIX,
+								cellVals[paramNumber].trim(), 256));
+			}
+		}
+		String result = _template;
+		for (String key : replacements.keySet())
+			result = replace(result, key, replacements.get(key), 256);
+		return result.equals("") ? _template : result;
+	}
+	
     private String buildMulti(final String cellValue) {
         final String[] cellVals = split( cellValue );
         String result = this._template;
 
         for ( int paramNumber = 0; paramNumber < cellVals.length; paramNumber++ ) {
-            final String replace = SnippetBuilder.PARAM_PREFIX + (paramNumber + 1);
+            final String replace = PARAM_PREFIX + (paramNumber + 1);
             result = replace( result,
                               replace,
                               cellVals[paramNumber].trim(),
@@ -106,7 +150,7 @@
     private String buildSingle(final String cellValue) {
 
         return replace( this._template,
-                        SnippetBuilder.PARAM,
+        				PARAM_STRING,
                         cellValue,
                         256 );
 

Modified: labs/jbossrules/trunk/drools-templates/src/test/java/org/drools/template/model/SnippetBuilderTest.java
===================================================================
--- labs/jbossrules/trunk/drools-templates/src/test/java/org/drools/template/model/SnippetBuilderTest.java	2010-06-21 08:41:48 UTC (rev 33567)
+++ labs/jbossrules/trunk/drools-templates/src/test/java/org/drools/template/model/SnippetBuilderTest.java	2010-06-21 13:31:16 UTC (rev 33568)
@@ -92,5 +92,59 @@
                       result );
 
     }
+    
+	public void testForAllAnd() {
+		final String snippet = "forall(&&){something == $}";
+		final SnippetBuilder snip = new SnippetBuilder(snippet);
+		final String result = snip.build("x");
+		assertEquals("something == x", result);
+	}
 
+	public void testForAllAndCSV() {
+		final String snippet = "forall(&&){something == $}";
+		final SnippetBuilder snip = new SnippetBuilder(snippet);
+		final String result = snip.build("x, y");
+		assertEquals("something == x && something == y", result);
+	}
+
+	public void testForAllAndNone() {
+		final String snippet = "forall(&&){something == $}";
+		final SnippetBuilder snip = new SnippetBuilder(snippet);
+		final String result = snip.build("");
+		assertEquals("forall(&&){something == $}", result);
+	}
+
+	public void testForAllAndCSVMultiple() {
+		final String snippet = "forall(&&){something == $ || something == $}";
+		final SnippetBuilder snip = new SnippetBuilder(snippet);
+		final String result = snip.build("x, y");
+		assertEquals(
+				"something == x || something == x && something == y || something == y",
+				result);
+	}
+
+	public void testForAllOr() {
+		final String snippet = "forall(||){something == $}";
+		final SnippetBuilder snip = new SnippetBuilder(snippet);
+		final String result = snip.build("x");
+		assertEquals("something == x", result);
+	}
+
+	public void testForAllOrMultiple() {
+		final String snippet = "forall(||){something == $} && forall(||){something < $}";
+		final SnippetBuilder snip = new SnippetBuilder(snippet);
+		final String result = snip.build("x, y");
+		assertEquals(
+				"something == x || something == y && something < x || something < y",
+				result);
+	}
+	
+	public void testForAllOrAndMultipleWithPrefix() {
+		final String snippet = "something == this && forall(||){something == $} && forall(&&){something < $}";
+		final SnippetBuilder snip = new SnippetBuilder(snippet);
+		final String result = snip.build("x, y");
+		assertEquals(
+				"something == this && something == x || something == y && something < x && something < y",
+				result);
+	}
 }
\ No newline at end of file



More information about the jboss-svn-commits mailing list