(1);
        actionParams.put("aspect-name", ContentModel.ASPECT_VERSIONABLE);        
        
        Rule rule = createRule(
        		RuleType.INBOUND, 
        		AddFeaturesActionExecuter.NAME, 
        		actionParams, 
        		NoConditionEvaluator.NAME, 
        		null);
        
        this.ruleService.saveRule(this.nodeRef, rule);        
        this.ruleService.disableRules(this.nodeRef);
        
        NodeRef newNodeRef = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                getContentProperties()).getChildRef();         
        addContentToNode(newNodeRef);
        assertFalse(this.nodeService.hasAspect(newNodeRef, ContentModel.ASPECT_VERSIONABLE));      
        
        this.ruleService.enableRules(this.nodeRef);
        
        NodeRef newNodeRef2 = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                getContentProperties()).getChildRef();        
        addContentToNode(newNodeRef2);
        assertTrue(this.nodeService.hasAspect(newNodeRef2, ContentModel.ASPECT_VERSIONABLE));       
    }
    
    /**
     * Adds content to a given node. 
     * 
     * Used to trigger rules of type of incomming.
     * 
     * @param nodeRef  the node reference
     */
    private void addContentToNode(NodeRef nodeRef)
    {
    	ContentWriter contentWriter = this.contentService.getWriter(nodeRef, ContentModel.PROP_CONTENT, true);
        contentWriter.setMimetype(MimetypeMap.MIMETYPE_TEXT_PLAIN);
        contentWriter.setEncoding("UTF-8");
    	assertNotNull(contentWriter);
    	contentWriter.putContent(STANDARD_TEXT_CONTENT + System.currentTimeMillis());
    }
    
    /**
     * Test checkMandatoryProperties method
     */
    public void testCheckMandatoryProperties()
    {
        Map actionParams = new HashMap(1);
        actionParams.put("aspect-name", ContentModel.ASPECT_VERSIONABLE);        
        
        Map condParams = new HashMap(1);
        // should be setting the condition parameter here
        
        Rule rule = createRule(
        		RuleType.INBOUND, 
        		AddFeaturesActionExecuter.NAME, 
        		actionParams, 
        		ComparePropertyValueEvaluator.NAME, 
        		condParams);
        
        this.ruleService.saveRule(this.nodeRef, rule);
        
        try
        {
            // Try and create a node .. should fail since the rule is invalid
            Map props2 = getContentProperties();
            props2.put(ContentModel.PROP_NAME, "bobbins.doc");
            NodeRef newNodeRef2 = this.nodeService.createNode(
                    this.nodeRef,
                    ContentModel.ASSOC_CHILDREN,                
                    QName.createQName(TEST_NAMESPACE, "children"),
                    ContentModel.TYPE_CONTENT,
                    props2).getChildRef();
            addContentToNode(newNodeRef2);
            fail("An exception should have been thrown since a mandatory parameter was missing from the condition.");
        }
        catch (Throwable ruleServiceException)
        {
            // Success since we where expecting the exception
        }
    }
    
	/**
     * Test:
     *          rule type:  inbound
     *          condition:  match-text(
     *          				text = .doc,
     *          				operation = CONTAINS)
     *          action:     add-features(
     *                          aspect-name = versionable)
     */
	public void testContainsTextCondition()
	{
		Map actionParams = new HashMap(1);
		actionParams.put("aspect-name", ContentModel.ASPECT_VERSIONABLE);        
        
        // ActionCondition parameter's 
		Map condParams = new HashMap(1);
		condParams.put(ComparePropertyValueEvaluator.PARAM_VALUE, ".doc");        
		
		Rule rule = createRule(
        		RuleType.INBOUND, 
        		AddFeaturesActionExecuter.NAME, 
        		actionParams, 
        		ComparePropertyValueEvaluator.NAME, 
        		condParams);
        
        this.ruleService.saveRule(this.nodeRef, rule);
		
		// Test condition failure
		Map props1 = new HashMap();
		props1.put(ContentModel.PROP_NAME, "bobbins.txt");
       // props1.put(ContentModel.PROP_CONTENT, CONTENT_DATA_TEXT);
		NodeRef newNodeRef = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                props1).getChildRef();   
		addContentToNode(newNodeRef);
        
        //Map map = this.nodeService.getProperties(newNodeRef);
        //String value = (String)this.nodeService.getProperty(newNodeRef, ContentModel.PROP_NAME);
        
        assertFalse(this.nodeService.hasAspect(newNodeRef, ContentModel.ASPECT_VERSIONABLE));  
		
		// Test condition success
		Map props2 = new HashMap();
		props2.put(ContentModel.PROP_NAME, "bobbins.doc");
        //props2.put(ContentModel.PROP_CONTENT, CONTENT_DATA_TEXT);
		NodeRef newNodeRef2 = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                props2).getChildRef();        
		addContentToNode(newNodeRef2);
        assertTrue(this.nodeService.hasAspect(
                newNodeRef2, 
                ContentModel.ASPECT_VERSIONABLE)); 
		
		try
		{
			// Test name not set
			NodeRef newNodeRef3 = this.nodeService.createNode(
	                this.nodeRef,
                    ContentModel.ASSOC_CHILDREN,                
	                QName.createQName(TEST_NAMESPACE, "children"),
	                ContentModel.TYPE_CONTENT,
                    getContentProperties()).getChildRef();      
			addContentToNode(newNodeRef3);
		}
		catch (RuleServiceException exception)
		{
			// Correct since text-match is a mandatory property
		}
        
        // Test begins with
        Map condParamsBegins = new HashMap(1);
        condParamsBegins.put(ComparePropertyValueEvaluator.PARAM_VALUE, "bob*");
        rule.getAction().removeAllActionConditions();
        ActionCondition condition1 = this.actionService.createActionCondition(ComparePropertyValueEvaluator.NAME, condParamsBegins);
        rule.getAction().addActionCondition(condition1);
        this.ruleService.saveRule(this.nodeRef, rule);
        Map propsx = new HashMap();
        propsx.put(ContentModel.PROP_NAME, "mybobbins.doc");
        //propsx.put(ContentModel.PROP_CONTENT, CONTENT_DATA_TEXT);
        NodeRef newNodeRefx = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                propsx).getChildRef();   
        addContentToNode(newNodeRefx);
        assertFalse(this.nodeService.hasAspect(newNodeRefx, ContentModel.ASPECT_VERSIONABLE));  
        Map propsy = new HashMap();
        propsy.put(ContentModel.PROP_NAME, "bobbins.doc");
        //propsy.put(ContentModel.PROP_CONTENT, CONTENT_DATA_TEXT);
        NodeRef newNodeRefy = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                propsy).getChildRef();   
        addContentToNode(newNodeRefy);
        assertTrue(this.nodeService.hasAspect(
                newNodeRefy, 
                ContentModel.ASPECT_VERSIONABLE)); 
        
        // Test ends with
        Map condParamsEnds = new HashMap(1);
        condParamsEnds.put(ComparePropertyValueEvaluator.PARAM_VALUE, "*s.doc");
        rule.getAction().removeAllActionConditions();
        ActionCondition condition2 = this.actionService.createActionCondition(ComparePropertyValueEvaluator.NAME, condParamsEnds);
        rule.getAction().addActionCondition(condition2);
        this.ruleService.saveRule(this.nodeRef, rule);
        Map propsa = new HashMap();
        propsa.put(ContentModel.PROP_NAME, "bobbins.document");
       // propsa.put(ContentModel.PROP_CONTENT, CONTENT_DATA_TEXT);
        NodeRef newNodeRefa = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                propsa).getChildRef(); 
        addContentToNode(newNodeRefa);
        assertFalse(this.nodeService.hasAspect(newNodeRefa, ContentModel.ASPECT_VERSIONABLE));  
        Map propsb = new HashMap();
        propsb.put(ContentModel.PROP_NAME, "bobbins.doc");
        //propsb.put(ContentModel.PROP_CONTENT, CONTENT_DATA_TEXT);
        NodeRef newNodeRefb = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT,
                propsb).getChildRef();   
        addContentToNode(newNodeRefb);
        assertTrue(this.nodeService.hasAspect(
                newNodeRefb, 
                ContentModel.ASPECT_VERSIONABLE)); 
	}
    
    public void testInboundRuleType()
    {
        Map params = new HashMap(1);
        params.put("aspect-name", ContentModel.ASPECT_VERSIONABLE);              
        Rule rule = createRule(
                RuleType.INBOUND, 
                AddFeaturesActionExecuter.NAME, 
                params, 
                NoConditionEvaluator.NAME, 
                null);
        
        this.ruleService.saveRule(this.nodeRef, rule);
        
        // Create a non-content node
        NodeRef newNodeRef =  this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTAINER).getChildRef();
        assertTrue(this.nodeService.hasAspect(newNodeRef, ContentModel.ASPECT_VERSIONABLE));
        
        // Create a content node
        NodeRef contentNodeRef = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT).getChildRef();        
        assertTrue(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE));        
        addContentToNode(contentNodeRef);            
        assertTrue(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE));
        
        // Create a node to be moved
        NodeRef moveNode = this.nodeService.createNode(
                newNodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT).getChildRef(); 
        addContentToNode(moveNode);
        assertFalse(this.nodeService.hasAspect(moveNode, ContentModel.ASPECT_VERSIONABLE));
        this.nodeService.moveNode(
                moveNode, 
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"));
        assertTrue(this.nodeService.hasAspect(moveNode, ContentModel.ASPECT_VERSIONABLE)); 
        
        // Enusre the rule type does not get fired when the node is updated
        this.nodeService.removeAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE);
        assertFalse(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE)); 
        this.nodeService.setProperty(contentNodeRef, ContentModel.PROP_NAME, "name.txt");
        assertFalse(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE));
        addContentToNode(contentNodeRef);
        assertFalse(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE));        
    }
    
    public void testUpdateRuleType()
    {
        Map params = new HashMap(1);
        params.put("aspect-name", ContentModel.ASPECT_VERSIONABLE);              
        Rule rule = createRule(
                RuleType.UPDATE, 
                AddFeaturesActionExecuter.NAME, 
                params, 
                NoConditionEvaluator.NAME, 
                null);
        
        this.ruleService.saveRule(this.nodeRef, rule);
        
        // Create a non-content node
        NodeRef newNodeRef =  this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_FOLDER).getChildRef();
        this.nodeService.removeAspect(newNodeRef, ContentModel.ASPECT_VERSIONABLE);
        assertFalse(this.nodeService.hasAspect(newNodeRef, ContentModel.ASPECT_VERSIONABLE));
        
        // Update the non-content node
        this.nodeService.setProperty(newNodeRef, ContentModel.PROP_NAME, "testName");
        assertTrue(this.nodeService.hasAspect(newNodeRef, ContentModel.ASPECT_VERSIONABLE));
        
        // Create a content node
        NodeRef contentNodeRef = this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_CONTENT).getChildRef();                
        nodeService.removeAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE);
        assertFalse(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE));        
        addContentToNode(contentNodeRef);            
        assertFalse(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE));
        addContentToNode(contentNodeRef);            
        assertTrue(this.nodeService.hasAspect(contentNodeRef, ContentModel.ASPECT_VERSIONABLE));
        
        // Create a non content node, setting a property at the same time
        Map props = new HashMap(1);
        props.put(ContentModel.PROP_NAME, "testName");
        NodeRef nodeRef2 =  this.nodeService.createNode(
                this.nodeRef,
                ContentModel.ASSOC_CHILDREN,                
                QName.createQName(TEST_NAMESPACE, "children"),
                ContentModel.TYPE_FOLDER,
                props).getChildRef();
        nodeService.removeAspect(nodeRef2, ContentModel.ASPECT_VERSIONABLE);
        assertFalse(this.nodeService.hasAspect(nodeRef2, ContentModel.ASPECT_VERSIONABLE));
        this.nodeService.setProperty(nodeRef2, ContentModel.PROP_NAME, "testName");
        assertFalse(this.nodeService.hasAspect(nodeRef2, ContentModel.ASPECT_VERSIONABLE));
        this.nodeService.setProperty(nodeRef2, ContentModel.PROP_NAME, "testName2");
        assertTrue(this.nodeService.hasAspect(nodeRef2, ContentModel.ASPECT_VERSIONABLE));
        
        transactionService.getRetryingTransactionHelper().doInTransaction(new RetryingTransactionCallback