mirror of
				https://github.com/node-red/node-red.git
				synced 2025-03-01 10:36:34 +00:00 
			
		
		
		
	Add Flow spec
This commit is contained in:
		@@ -1,5 +1,5 @@
 | 
			
		||||
/**
 | 
			
		||||
 * Copyright 2014 IBM Corp.
 | 
			
		||||
 * Copyright 2015 IBM Corp.
 | 
			
		||||
 *
 | 
			
		||||
 * Licensed under the Apache License, Version 2.0 (the "License");
 | 
			
		||||
 * you may not use this file except in compliance with the License.
 | 
			
		||||
@@ -210,6 +210,7 @@ function Flow(config) {
 | 
			
		||||
    
 | 
			
		||||
    this.activeNodes = {};
 | 
			
		||||
    this.subflowInstanceNodes = {};
 | 
			
		||||
    this.started = false;
 | 
			
		||||
 | 
			
		||||
    this.parseConfig(config);
 | 
			
		||||
    
 | 
			
		||||
@@ -251,7 +252,6 @@ Flow.prototype.parseConfig = function(config) {
 | 
			
		||||
        nodeType = nodeConfig.type;
 | 
			
		||||
        
 | 
			
		||||
        if (nodeConfig.credentials) {
 | 
			
		||||
            credentials.extract(nodeConfig);
 | 
			
		||||
            delete nodeConfig.credentials;
 | 
			
		||||
        }
 | 
			
		||||
        
 | 
			
		||||
@@ -297,6 +297,7 @@ Flow.prototype.parseConfig = function(config) {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
Flow.prototype.start = function() {
 | 
			
		||||
    this.started = true;
 | 
			
		||||
    if (this.missingTypes.length > 0) {
 | 
			
		||||
        throw new Error("missing types");
 | 
			
		||||
    }
 | 
			
		||||
@@ -354,6 +355,7 @@ Flow.prototype.stop = function(nodeList) {
 | 
			
		||||
        }
 | 
			
		||||
        when.settle(promises).then(function() {
 | 
			
		||||
            events.emit("nodes-stopped");
 | 
			
		||||
            flow.started = false;
 | 
			
		||||
            resolve();
 | 
			
		||||
        });
 | 
			
		||||
    });
 | 
			
		||||
@@ -368,7 +370,7 @@ Flow.prototype.typeRegistered = function(type) {
 | 
			
		||||
        var i = this.missingTypes.indexOf(type);
 | 
			
		||||
        if (i != -1) {
 | 
			
		||||
            this.missingTypes.splice(i,1);
 | 
			
		||||
            if (this.missingTypes.length === 0) {
 | 
			
		||||
            if (this.missingTypes.length === 0 && this.started) {
 | 
			
		||||
                this.start();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
@@ -505,7 +507,7 @@ Flow.prototype.diffFlow = function(config) {
 | 
			
		||||
    
 | 
			
		||||
    this.config.forEach(function(node) {
 | 
			
		||||
        for (var prop in node) {
 | 
			
		||||
            if (node.hasOwnProperty(prop) && prop != "z") {
 | 
			
		||||
            if (node.hasOwnProperty(prop) && prop != "z" && prop != "id" && prop != "wires") {
 | 
			
		||||
                // This node has a property that references a changed node
 | 
			
		||||
                // Assume it is a config node change and mark this node as
 | 
			
		||||
                // changed.
 | 
			
		||||
@@ -553,7 +555,7 @@ Flow.prototype.diffFlow = function(config) {
 | 
			
		||||
        buildNodeLinks(newLinks,node,configNodes);
 | 
			
		||||
    });
 | 
			
		||||
    
 | 
			
		||||
    var markLinkedNodes = function(linkChanged,changedNodes,linkMap,allNodes) {
 | 
			
		||||
    var markLinkedNodes = function(linkChanged,otherChangedNodes,linkMap,allNodes) {
 | 
			
		||||
        var stack = Object.keys(changedNodes);
 | 
			
		||||
        var visited = {};
 | 
			
		||||
        
 | 
			
		||||
@@ -563,8 +565,8 @@ Flow.prototype.diffFlow = function(config) {
 | 
			
		||||
            var linkedNodes = linkMap[id];
 | 
			
		||||
            if (linkedNodes) {
 | 
			
		||||
                for (var i=0;i<linkedNodes.length;i++) {
 | 
			
		||||
                    linkedNodeId = linkedNodes[i];
 | 
			
		||||
                    if (changedNodes[linkedNodeId] || linkChanged[linkedNodeId]) {
 | 
			
		||||
                    var linkedNodeId = linkedNodes[i];
 | 
			
		||||
                    if (changedNodes[linkedNodeId] || deletedNodes[linkedNodeId] || otherChangedNodes[linkedNodeId] || linkChanged[linkedNodeId]) {
 | 
			
		||||
                        // Do nothing - this linked node is already marked as changed, so will get done
 | 
			
		||||
                    } else {
 | 
			
		||||
                        linkChanged[linkedNodeId] = true;
 | 
			
		||||
@@ -575,12 +577,11 @@ Flow.prototype.diffFlow = function(config) {
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    
 | 
			
		||||
    markLinkedNodes(linkChangedNodes,changedNodes,newLinks,configNodes);
 | 
			
		||||
    markLinkedNodes(linkChangedNodes,deletedNodes,activeLinks,flow.allNodes);
 | 
			
		||||
    
 | 
			
		||||
    markLinkedNodes(linkChangedNodes,{},newLinks,configNodes);
 | 
			
		||||
    markLinkedNodes(linkChangedNodes,{},activeLinks,flow.allNodes);
 | 
			
		||||
    
 | 
			
		||||
    var modifiedLinkNodes = {};
 | 
			
		||||
    
 | 
			
		||||
 | 
			
		||||
    config.forEach(function(node) {
 | 
			
		||||
        if (!changedNodes[node.id]) {
 | 
			
		||||
            // only concerned about unchanged nodes whose wiring may have changed
 | 
			
		||||
@@ -596,18 +597,21 @@ Flow.prototype.diffFlow = function(config) {
 | 
			
		||||
            newNodeLinks.forEach(function(link) {
 | 
			
		||||
                if (newLinkMap[link] != oldLinkMap[link]) {
 | 
			
		||||
                    modifiedLinkNodes[node.id] = node;
 | 
			
		||||
                    modifiedLinkNodes[link] = configNodes[link];
 | 
			
		||||
                    linkChangedNodes[node.id] = node;
 | 
			
		||||
                    linkChangedNodes[link] = configNodes[link];
 | 
			
		||||
                    if (!changedNodes[link] && !deletedNodes[link]) {
 | 
			
		||||
                        modifiedLinkNodes[link] = configNodes[link];
 | 
			
		||||
                        linkChangedNodes[link] = configNodes[link];
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            
 | 
			
		||||
            oldNodeLinks.forEach(function(link) {
 | 
			
		||||
                if (newLinkMap[link] != oldLinkMap[link]) {
 | 
			
		||||
                    modifiedLinkNodes[node.id] = node;
 | 
			
		||||
                    modifiedLinkNodes[link] = configNodes[link];
 | 
			
		||||
                    linkChangedNodes[node.id] = node;
 | 
			
		||||
                    linkChangedNodes[link] = configNodes[link];
 | 
			
		||||
                    if (!changedNodes[link] && !deletedNodes[link]) {
 | 
			
		||||
                        modifiedLinkNodes[link] = configNodes[link];
 | 
			
		||||
                        linkChangedNodes[link] = configNodes[link];
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
        }
 | 
			
		||||
@@ -615,7 +619,6 @@ Flow.prototype.diffFlow = function(config) {
 | 
			
		||||
    
 | 
			
		||||
    markLinkedNodes(linkChangedNodes,modifiedLinkNodes,newLinks,configNodes);
 | 
			
		||||
    
 | 
			
		||||
    
 | 
			
		||||
    //config.forEach(function(n) {
 | 
			
		||||
    //    console.log((changedNodes[n.id]!=null)?"[C]":"[ ]",(linkChangedNodes[n.id]!=null)?"[L]":"[ ]","[ ]",n.id,n.type,n.name);
 | 
			
		||||
    //});
 | 
			
		||||
 
 | 
			
		||||
@@ -1,5 +1,5 @@
 | 
			
		||||
/**
 | 
			
		||||
 * Copyright 2014 IBM Corp.
 | 
			
		||||
 * Copyright 2014, 2015 IBM Corp.
 | 
			
		||||
 *
 | 
			
		||||
 * Licensed under the Apache License, Version 2.0 (the "License");
 | 
			
		||||
 * you may not use this file except in compliance with the License.
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										12
									
								
								settings.js
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								settings.js
									
									
									
									
									
								
							@@ -20,6 +20,18 @@
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
module.exports = {
 | 
			
		||||
    
 | 
			
		||||
    adminAuth: {
 | 
			
		||||
        type: "credentials",
 | 
			
		||||
        users: [ {
 | 
			
		||||
            username: "nol",
 | 
			
		||||
            password: "5f4dcc3b5aa765d61d8327deb882cf99", // password
 | 
			
		||||
            permissions: "*"
 | 
			
		||||
        }],
 | 
			
		||||
        anonymous: {
 | 
			
		||||
            permissions: "read"
 | 
			
		||||
        }
 | 
			
		||||
    },
 | 
			
		||||
    // the tcp port that the Node-RED web server is listening on
 | 
			
		||||
    uiPort: 1880,
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -0,0 +1,316 @@
 | 
			
		||||
/**
 | 
			
		||||
 * Copyright 2015 IBM Corp.
 | 
			
		||||
 *
 | 
			
		||||
 * 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.
 | 
			
		||||
 **/
 | 
			
		||||
 
 | 
			
		||||
 | 
			
		||||
var should = require("should");
 | 
			
		||||
var sinon = require('sinon');
 | 
			
		||||
var clone = require('clone');
 | 
			
		||||
var Flow = require("../../../red/nodes/Flow");
 | 
			
		||||
 | 
			
		||||
var typeRegistry = require("../../../red/nodes/registry");
 | 
			
		||||
var credentials = require("../../../red/nodes/credentials");
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
describe('Flow', function() {
 | 
			
		||||
    describe('#constructor',function() {
 | 
			
		||||
        it('called with an empty flow',function() {
 | 
			
		||||
            var config = [];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            config.should.eql(flow.getFlow());
 | 
			
		||||
            
 | 
			
		||||
            var nodeCount = 0;
 | 
			
		||||
            flow.eachNode(function(node) {
 | 
			
		||||
                nodeCount++;
 | 
			
		||||
            });
 | 
			
		||||
            
 | 
			
		||||
            nodeCount.should.equal(0);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('called with a non-empty flow with no missing types', function() {
 | 
			
		||||
            var getType = sinon.stub(typeRegistry,"get",function(type) {
 | 
			
		||||
                // For this test, don't care what the actual type is, just
 | 
			
		||||
                // that this returns a non-false result
 | 
			
		||||
                return {};
 | 
			
		||||
            });
 | 
			
		||||
            try {
 | 
			
		||||
                var config = [{id:"123",type:"test"}];
 | 
			
		||||
                var flow = new Flow(config);
 | 
			
		||||
                config.should.eql(flow.getFlow());
 | 
			
		||||
                
 | 
			
		||||
                flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            } finally {
 | 
			
		||||
                getType.restore();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies missing types in a flow', function() {
 | 
			
		||||
            var getType = sinon.stub(typeRegistry,"get",function(type) {
 | 
			
		||||
                if (type == "test") {
 | 
			
		||||
                    return {};
 | 
			
		||||
                } else {
 | 
			
		||||
                    return null;
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            try {
 | 
			
		||||
                var config = [{id:"123",type:"test"},{id:"456",type:"test1"},{id:"789",type:"test2"}];
 | 
			
		||||
                var flow = new Flow(config);
 | 
			
		||||
                config.should.eql(flow.getFlow());
 | 
			
		||||
                
 | 
			
		||||
                flow.getMissingTypes().should.eql(["test1","test2"]);
 | 
			
		||||
            } finally {
 | 
			
		||||
                getType.restore();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('extracts node credentials', function() {
 | 
			
		||||
            var getType = sinon.stub(typeRegistry,"get",function(type) {
 | 
			
		||||
                // For this test, don't care what the actual type is, just
 | 
			
		||||
                // that this returns a non-false result
 | 
			
		||||
                return {};
 | 
			
		||||
            });
 | 
			
		||||
            
 | 
			
		||||
            try {
 | 
			
		||||
                var config = [{id:"123",type:"test",credentials:{a:1,b:2}}];
 | 
			
		||||
                var resultingConfig = clone(config);
 | 
			
		||||
                delete resultingConfig[0].credentials;
 | 
			
		||||
                var flow = new Flow(config);
 | 
			
		||||
                flow.getFlow().should.eql(resultingConfig);
 | 
			
		||||
                flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            } finally {
 | 
			
		||||
                getType.restore();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
    });
 | 
			
		||||
    describe('#start',function() {
 | 
			
		||||
 | 
			
		||||
        it('prevents a flow with missing types from starting', function() {
 | 
			
		||||
            var getType = sinon.stub(typeRegistry,"get",function(type) {
 | 
			
		||||
                if (type == "test") {
 | 
			
		||||
                    return {};
 | 
			
		||||
                } else {
 | 
			
		||||
                    return null;
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            try {
 | 
			
		||||
                var config = [{id:"123",type:"test"},{id:"456",type:"test1"},{id:"789",type:"test2"}];
 | 
			
		||||
                var flow = new Flow(config);
 | 
			
		||||
                flow.getMissingTypes().should.have.length(2);
 | 
			
		||||
    
 | 
			
		||||
                /*jshint immed: false */
 | 
			
		||||
                (function() {
 | 
			
		||||
                    flow.start();
 | 
			
		||||
                }).should.throw();
 | 
			
		||||
            } finally {
 | 
			
		||||
                getType.restore();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
    });
 | 
			
		||||
    
 | 
			
		||||
    describe('missing types',function() {
 | 
			
		||||
        it('removes missing types as they are registered', function() {
 | 
			
		||||
            var getType = sinon.stub(typeRegistry,"get",function(type) {
 | 
			
		||||
                if (type == "test") {
 | 
			
		||||
                    return {};
 | 
			
		||||
                } else {
 | 
			
		||||
                    return null;
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            var flowStart;
 | 
			
		||||
            try {
 | 
			
		||||
                var config = [{id:"123",type:"test"},{id:"456",type:"test1"},{id:"789",type:"test2"}];
 | 
			
		||||
                var flow = new Flow(config);
 | 
			
		||||
    
 | 
			
		||||
                flowStart = sinon.stub(flow,"start",function() {this.started = true;});
 | 
			
		||||
                config.should.eql(flow.getFlow());
 | 
			
		||||
                
 | 
			
		||||
                flow.getMissingTypes().should.eql(["test1","test2"]);
 | 
			
		||||
                
 | 
			
		||||
                flow.typeRegistered("test1");
 | 
			
		||||
                flow.getMissingTypes().should.eql(["test2"]);
 | 
			
		||||
                flowStart.called.should.be.false;
 | 
			
		||||
    
 | 
			
		||||
                flow.typeRegistered("test2");
 | 
			
		||||
                flow.getMissingTypes().should.eql([]);
 | 
			
		||||
                flowStart.called.should.be.false;
 | 
			
		||||
            } finally {
 | 
			
		||||
                flowStart.restore();
 | 
			
		||||
                getType.restore();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('starts flows once all missing types are registered', function() {
 | 
			
		||||
            var getType = sinon.stub(typeRegistry,"get",function(type) {
 | 
			
		||||
                if (type == "test") {
 | 
			
		||||
                    return {};
 | 
			
		||||
                } else {
 | 
			
		||||
                    return null;
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            var flowStart;
 | 
			
		||||
            try {
 | 
			
		||||
                var config = [{id:"123",type:"test"},{id:"456",type:"test1"},{id:"789",type:"test2"}];
 | 
			
		||||
                var flow = new Flow(config);
 | 
			
		||||
    
 | 
			
		||||
                // First call to .start throws err due to missing types
 | 
			
		||||
                /*jshint immed: false */
 | 
			
		||||
                (function() {
 | 
			
		||||
                    flow.start();
 | 
			
		||||
                }).should.throw();
 | 
			
		||||
    
 | 
			
		||||
                // Stub .start so when missing types are registered, we don't actually try starting them
 | 
			
		||||
                flowStart = sinon.stub(flow,"start",function() {});
 | 
			
		||||
                config.should.eql(flow.getFlow());
 | 
			
		||||
                
 | 
			
		||||
                flow.getMissingTypes().should.eql(["test1","test2"]);
 | 
			
		||||
                
 | 
			
		||||
                flow.typeRegistered("test1");
 | 
			
		||||
                flow.typeRegistered("test2");
 | 
			
		||||
                flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
                flowStart.called.should.be.true;
 | 
			
		||||
            } finally {
 | 
			
		||||
                flowStart.restore();
 | 
			
		||||
                getType.restore();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
    });
 | 
			
		||||
    
 | 
			
		||||
    describe('#diffFlow',function() {
 | 
			
		||||
        var getType;
 | 
			
		||||
        before(function() {
 | 
			
		||||
            getType = sinon.stub(typeRegistry,"get",function(type) {
 | 
			
		||||
                // For this test, don't care what the actual type is, just
 | 
			
		||||
                // that this returns a non-false result
 | 
			
		||||
                return {};
 | 
			
		||||
            });
 | 
			
		||||
                
 | 
			
		||||
        });
 | 
			
		||||
        after(function() {
 | 
			
		||||
            getType.restore();
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('handles an identical configuration', function() {
 | 
			
		||||
            var config = [{id:"123",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(config);
 | 
			
		||||
        
 | 
			
		||||
            diffResult.should.have.property("deleted",[]);
 | 
			
		||||
            diffResult.should.have.property("changed",[]);
 | 
			
		||||
            diffResult.should.have.property("linked",[]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",[]);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies nodes with changed properties, including downstream linked', function() {
 | 
			
		||||
            var config =    [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var newConfig = [{id:"1",type:"test",foo:"b",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(newConfig);
 | 
			
		||||
        
 | 
			
		||||
            diffResult.should.have.property("deleted",[]);
 | 
			
		||||
            diffResult.should.have.property("changed",["1"]);
 | 
			
		||||
            diffResult.should.have.property("linked",["2"]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",[]);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies nodes with changed properties, including upstream linked', function() {
 | 
			
		||||
            var config =    [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var newConfig = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"c",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(newConfig);
 | 
			
		||||
        
 | 
			
		||||
            diffResult.should.have.property("deleted",[]);
 | 
			
		||||
            diffResult.should.have.property("changed",["2"]);
 | 
			
		||||
            diffResult.should.have.property("linked",["1"]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",[]);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies nodes with changed wiring', function() {
 | 
			
		||||
            var config = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var newConfig = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[2]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(newConfig);
 | 
			
		||||
        
 | 
			
		||||
            diffResult.should.have.property("deleted",[]);
 | 
			
		||||
            diffResult.should.have.property("changed",[]);
 | 
			
		||||
            diffResult.should.have.property("linked",["1","2"]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",["2"]);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies nodes with changed wiring - second connection added', function() {
 | 
			
		||||
            var config = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var newConfig = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1],[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(newConfig);
 | 
			
		||||
        
 | 
			
		||||
            diffResult.should.have.property("deleted",[]);
 | 
			
		||||
            diffResult.should.have.property("changed",[]);
 | 
			
		||||
            diffResult.should.have.property("linked",["1","2"]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",["2"]);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies nodes with changed wiring - second connection removed', function() {
 | 
			
		||||
            var config = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1],[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var newConfig = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(newConfig);
 | 
			
		||||
        
 | 
			
		||||
            diffResult.should.have.property("deleted",[]);
 | 
			
		||||
            diffResult.should.have.property("changed",[]);
 | 
			
		||||
            diffResult.should.have.property("linked",["1","2"]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",["2"]);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies new nodes', function() {
 | 
			
		||||
            var config = [{id:"1",type:"test",foo:"a",wires:[]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var newConfig = [{id:"1",type:"test",foo:"a",wires:[]},{id:"2",type:"test",bar:"b",wires:[[1]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(newConfig);
 | 
			
		||||
 | 
			
		||||
            diffResult.should.have.property("deleted",[]);
 | 
			
		||||
            diffResult.should.have.property("changed",["2"]);
 | 
			
		||||
            diffResult.should.have.property("linked",["1"]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",[]);
 | 
			
		||||
        });
 | 
			
		||||
        
 | 
			
		||||
        it('identifies deleted nodes', function() {
 | 
			
		||||
            var config = [{id:"1",type:"test",foo:"a",wires:[[2]]},{id:"2",type:"test",bar:"b",wires:[[3]]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var newConfig = [{id:"1",type:"test",foo:"a",wires:[]},{id:"3",type:"test",foo:"a",wires:[]}];
 | 
			
		||||
            var flow = new Flow(config);
 | 
			
		||||
            flow.getMissingTypes().should.have.length(0);
 | 
			
		||||
            
 | 
			
		||||
            var diffResult = flow.diffFlow(newConfig);
 | 
			
		||||
 | 
			
		||||
            diffResult.should.have.property("deleted",["2"]);
 | 
			
		||||
            diffResult.should.have.property("changed",[]);
 | 
			
		||||
            diffResult.should.have.property("linked",["1","3"]);
 | 
			
		||||
            diffResult.should.have.property("wiringChanged",["1"]);
 | 
			
		||||
        });
 | 
			
		||||
    });
 | 
			
		||||
});
 | 
			
		||||
		Reference in New Issue
	
	Block a user