Exemplo n.º 1
0
        public IBehaviour Setup(Actor target)
        {
            INodeInstance[] behaviourTokens = new INodeInstance[Nodes.Length];

            int nodeCount = Nodes.Length;

            // Map and create tokens
            for (int i = 0; i < nodeCount; i++)
            {
                var node = Nodes[i];
                behaviourTokens[i] = node.Create();
            }

            var graphInstance = new GraphInstance(this, behaviourTokens);

            // Connect the token sockets
            for (int i = 0; i < nodeCount; i++)
            {
                Nodes[i].ConnectToken(graphInstance, behaviourTokens[i]);
            }

            // Setup tokens
            for (int i = 0; i < nodeCount; i++)
            {
                Nodes[i].Setup(graphInstance, behaviourTokens[i], target);
            }

            return(graphInstance);
        }
Exemplo n.º 2
0
        public virtual void Subscribe(INodeInstance node, Action callback)
        {
            if (Consumers == null)
            {
                Consumers = new List <ConnectionSubscription>();
            }

            var subscription = new ConnectionSubscription();

            foreach (var previousSubscribers in Consumers)
            {
                if (subscription.Node == previousSubscribers.Node)
                {
                    subscription = previousSubscribers;
                }
            }
            if (subscription.Node == null)
            {
                subscription = new ConnectionSubscription(node);
                subscription.Callbacks.Add(callback);
                Consumers.Add(subscription);
            }
            else
            {
                subscription.Callbacks.Add(callback);
            }
        }
Exemplo n.º 3
0
 public HotNodeService(INodeInstance nodeInstance)
 {
     _nodeInstance = nodeInstance;
     _nodeProcess  = (Process)typeof(OutOfProcessNodeInstance)
                     .GetField("_nodeProcess", BindingFlags.Instance | BindingFlags.NonPublic)
                     .GetValue(_nodeInstance);
 }
Exemplo n.º 4
0
        private async Task <T> InvokeExportWithPossibleRetryAsync <T>(string moduleName, string exportedFunctionName, object[] args, bool allowRetry, CancellationToken cancellationToken)
        {
            this.ThrowAnyOutstandingDelayedDisposalException();
            var nodeInstance = this.GetOrCreateCurrentNodeInstance();

            try {
                return(await nodeInstance.InvokeExportAsync <T>(cancellationToken, moduleName, exportedFunctionName, args));
            } catch (NodeInvocationException ex) {
                // If the Node instance can't complete the invocation because it needs to restart (e.g., because the underlying
                // Node process has exited, or a file it depends on has changed), then we make one attempt to restart transparently.
                if (allowRetry && ex.NodeInstanceUnavailable)
                {
                    // Perform the retry after clearing away the old instance
                    // Since we disposal is delayed even though the node instance is replaced immediately, this produces the
                    // "connection draining" feature whereby in-flight RPC calls are given a certain period to complete.
                    lock (this._currentNodeInstanceAccessLock) {
                        if (this._currentNodeInstance == nodeInstance)
                        {
                            var disposalDelay = ex.AllowConnectionDraining ? ConnectionDrainingTimespan : TimeSpan.Zero;
                            this.DisposeNodeInstance(this._currentNodeInstance, disposalDelay);
                            this._currentNodeInstance = null;
                        }
                    }

                    // One the next call, don't allow retries, because we could get into an infinite retry loop, or a long retry
                    // loop that masks an underlying problem. A newly-created Node instance should be able to accept invocations,
                    // or something more serious must be wrong.
                    return(await this.InvokeExportWithPossibleRetryAsync <T>(moduleName, exportedFunctionName, args, /* allowRetry */ false, cancellationToken));
                }
                else
                {
                    throw;
                }
            }
        }
Exemplo n.º 5
0
        public void Setup()
        {
            int nodeCount = Template.Nodes.Length;

            // Start allowing events to fire
            for (int i = 0; i < nodeCount; i++)
            {
                var nodeInstance = nodeInstances[i];
                var nodeInputs   = allInputs[i];

                if (nodeInputs == null)
                {
                    continue;
                }

                foreach (var input in nodeInputs)
                {
                    connections[input.ConnectionId].RegisterInput(nodeInstance);
                }
            }

            // Run node setup process
            for (int i = 0; i < nodeCount; i++)
            {
                currentNode = nodeInstances[i];
                Template.Nodes[i].Setup(this, currentNode);
            }

            // Release all buffered events.
            foreach (var connection in connections)
            {
                connection.BufferEvents = false;
            }
        }
Exemplo n.º 6
0
        public override Boolean take(IToken token)
        {
            Boolean oldAlive = token.IsAlive;

            EdgeInstanceEvent e = new EdgeInstanceEvent(this);

            e.Token     = token;
            e.EventType = EdgeInstanceEventEnum.ON_TAKING_THE_TOKEN;

            for (int i = 0; this.eventListeners != null && i < this.eventListeners.Count; i++)
            {
                IEdgeInstanceEventListener listener = this.eventListeners[i];
                listener.onEdgeInstanceEventFired(e);
            }


            Boolean newAlive = token.IsAlive;

            if (!newAlive)
            {//循环条件不满足,则恢复token的alive标示
                token.IsAlive = oldAlive;
                return(newAlive);
            }
            else
            {//否则流转到下一个节点
                INodeInstance nodeInst = this.LeavingNodeInstance;
                token.Value = this.Weight;
                nodeInst.fire(token);//触发同步器节点
                return(newAlive);
            }
        }
Exemplo n.º 7
0
        public virtual void Unsubscribe(INodeInstance node, Action callback)
        {
            if (Consumers == null)
            {
                return;
            }

            for (int i = Consumers.Count - 1; i >= 0; i--)
            {
                var subscriber = Consumers[i];

                if (subscriber.Node == node)
                {
                    for (int j = subscriber.Callbacks.Count - 1; j >= 0; j--)
                    {
                        var findCallback = subscriber.Callbacks[j];

                        if (callback == findCallback)
                        {
                            subscriber.Callbacks.RemoveAt(j);
                        }
                    }
                }
            }
        }
Exemplo n.º 8
0
        public ManifestCaptureGraphInstance(Node singleNodeGraph)
        {
            node     = singleNodeGraph;
            instance = node.Create();

            node.Inputs(this, instance);
            node.Outputs(this, instance);
        }
Exemplo n.º 9
0
        public void RegisterInput(INodeInstance node)
        {
            if (Consumers == null)
            {
                Consumers = new List <ConnectionSubscription>();
            }

            Consumers.Add(new ConnectionSubscription(node));
        }
Exemplo n.º 10
0
 public void Dispose()
 {
     lock (_currentNodeInstanceAccessLock) {
         if (_currentNodeInstance != null)
         {
             DisposeNodeInstance(_currentNodeInstance, delay: TimeSpan.Zero);
             _currentNodeInstance = null;
         }
     }
 }
Exemplo n.º 11
0
        public void Setup(Actor target)
        {
            int nodeCount = graph.Nodes.Length;

            for (int i = 0; i < nodeCount; i++)
            {
                currentNode = nodeInstances[i];
                graph.Nodes[i].Setup(this, currentNode, target);
            }
        }
Exemplo n.º 12
0
        public ManifestCaptureGraphInstance(NodeTemplate singleNodeGraph)
        {
            node     = singleNodeGraph;
            instance = node.CreateInstance();

            var connectionMapper = new ConnectionMapper(instance, this);

            node.Inputs(connectionMapper, instance);
            node.Outputs(connectionMapper, instance);
        }
Exemplo n.º 13
0
        public GraphInstance(Graph template, IDictionary <LocalId, JObject> data = null)
        {
            Template = template;

            int nodeCount = template.Nodes.Length;

            nodeInstances = new INodeInstance[nodeCount];

            var serializer = new JsonSerializer();

            serializer.Converters.Add(new OutputConverter());

            // Map and create tokens
            for (int i = 0; i < nodeCount; i++)
            {
                var node = template.Nodes[i];

                var instance = node.CreateInstance();

                if (data != null && data.TryGetValue(node.Id, out var instanceData))
                {
                    using (var sr = instanceData.CreateReader())
                    {
                        serializer.Populate(sr, instance);
                    }
                }

                nodeInstances[i] = instance;
            }

            connections = new IConnection[template.ConnectionsCount];

            // Allow all outputs to make their output type visible
            allOutputs = new OutputMap[nodeCount][];
            for (int i = 0; i < nodeCount; i++)
            {
                currentNode   = nodeInstances[i];
                allOutputs[i] = template.Nodes[i].Outputs(this, currentNode);
            }

            // Allow inputs to subscribe to those outputs.
            allInputs = new InputMap[nodeCount][];
            for (int i = 0; i < nodeCount; i++)
            {
                currentNode  = nodeInstances[i];
                allInputs[i] = template.Nodes[i].Inputs(this, currentNode);
            }

            // Stop events from taking effect immediately.
            foreach (var connection in connections)
            {
                connection.BufferEvents = true;
            }
        }
Exemplo n.º 14
0
        public void Dispose()
        {
            lock (this._currentNodeInstanceAccessLock) {
                if (this._currentNodeInstance != null)
                {
                    this.DisposeNodeInstance(this._currentNodeInstance, delay: TimeSpan.Zero);
                    this._currentNodeInstance = null;
                }

                HostingEnvironment.UnregisterObject(this);
            }
        }
Exemplo n.º 15
0
        private INodeInstance GetOrCreateCurrentNodeInstance()
        {
            var instance = this._currentNodeInstance;

            if (instance == null)
            {
                lock (this._currentNodeInstanceAccessLock) {
                    instance = this._currentNodeInstance;
                    if (instance == null)
                    {
                        instance = this._currentNodeInstance = this.CreateNewNodeInstance();
                    }
                }
            }

            return(instance);
        }
Exemplo n.º 16
0
        public GraphInstance(Graph graph, IDictionary <LocalId, JObject> data = null)
        {
            this.graph = graph;

            int nodeCount = graph.Nodes.Length;

            nodeInstances = new INodeInstance[nodeCount];

            // Map and create tokens
            for (int i = 0; i < nodeCount; i++)
            {
                var node = graph.Nodes[i];

                if (data != null && data.TryGetValue(node.Id, out var instanceData))
                {
                    var serializer = new JsonSerializer();
                    serializer.Converters.Add(new OutputConverter());

                    nodeInstances[i] = (INodeInstance)instanceData.ToObject(node.MetadataType, serializer);
                }
                else
                {
                    nodeInstances[i] = node.Create();
                }
            }

            connections = new IConnection[graph.ConnectionsCount];

            // Allow all outputs to make their output type visible
            allOutputs = new OutputMap[nodeCount][];
            for (int i = 0; i < nodeCount; i++)
            {
                currentNode   = nodeInstances[i];
                allOutputs[i] = graph.Nodes[i].Outputs(this, currentNode);
            }

            // Allow inputs to subscribe to those outputs.
            allInputs = new InputMap[nodeCount][];
            for (int i = 0; i < nodeCount; i++)
            {
                currentNode  = nodeInstances[i];
                allInputs[i] = graph.Nodes[i].Inputs(this, currentNode);
            }
        }
Exemplo n.º 17
0
 private void DisposeNodeInstance(INodeInstance nodeInstance, TimeSpan delay)
 {
     if (delay == TimeSpan.Zero)
     {
         nodeInstance.Dispose();
     }
     else
     {
         Task.Run(async() => {
             try {
                 await Task.Delay(delay);
                 nodeInstance.Dispose();
             } catch (Exception ex) {
                 // Nothing's waiting for the delayed disposal task, so any exceptions in it would
                 // by default just get ignored. To make these discoverable, capture them here so
                 // they can be rethrown to the next caller to InvokeExportAsync.
                 this._instanceDelayedDisposalException = ex;
             }
         });
     }
 }
Exemplo n.º 18
0
        public override Boolean take(IToken token)
        {
            EdgeInstanceEvent e = new EdgeInstanceEvent(this);

            e.Token     = token;
            e.EventType = EdgeInstanceEventEnum.ON_TAKING_THE_TOKEN;

            for (int i = 0; this.eventListeners != null && i < this.eventListeners.Count; i++)
            {
                IEdgeInstanceEventListener listener = this.eventListeners[i];
                listener.onEdgeInstanceEventFired(e);//调用TransitionInstanceExtension 来计算弧线上的条件表达式
            }

            INodeInstance nodeInst = this.LeavingNodeInstance; //获取到流向哪个节点

            token.Value = this.Weight;                         //获取到弧线上的权值
            Boolean alive = token.IsAlive;

            nodeInst.fire(token);//节点触发

            return(alive);
        }
Exemplo n.º 19
0
        /// <summary>wangmj  初始化一个工作流网实例,将引擎的扩展属性,注入到对应的工作流元素中</summary>
        /// <param name="process"></param>
        /// <param name="kenelExtensions"></param>
        public NetInstance(WorkflowProcess process, Dictionary <String, List <IKernelExtension> > kenelExtensions)
        {
            this.workflowProcess = process;

            //开始节点
            StartNode startNode = workflowProcess.StartNode;

            StartNodeInstance = new StartNodeInstance(startNode);
            List <IKernelExtension> extensionList = kenelExtensions[StartNodeInstance.ExtensionTargetName];

            for (int i = 0; extensionList != null && i < extensionList.Count; i++)
            {
                IKernelExtension extension = extensionList[i];
                StartNodeInstance.registExtension(extension);
            }
            //this.StartNodeInstance = StartNodeInstance; 自身赋值自身没用。
            wfElementInstanceMap.Add(startNode.Id, StartNodeInstance);

            //活动节点activity
            List <Activity> activities = workflowProcess.Activities;

            for (int i = 0; i < activities.Count; i++)
            {
                Activity         activity         = (Activity)activities[i];
                ActivityInstance activityInstance = new ActivityInstance(activity);
                extensionList = kenelExtensions[activityInstance.ExtensionTargetName];
                for (int j = 0; extensionList != null && j < extensionList.Count; j++)
                {
                    IKernelExtension extension = extensionList[j];
                    activityInstance.registExtension(extension);
                }
                wfElementInstanceMap.Add(activity.Id, activityInstance);
            }

            //同步器节点
            List <Synchronizer> synchronizers = workflowProcess.Synchronizers;

            for (int i = 0; i < synchronizers.Count; i++)
            {
                Synchronizer         synchronizer         = (Synchronizer)synchronizers[i];
                SynchronizerInstance synchronizerInstance = new SynchronizerInstance(synchronizer);
                extensionList = kenelExtensions[synchronizerInstance.ExtensionTargetName];
                for (int j = 0; extensionList != null && j < extensionList.Count; j++)
                {
                    IKernelExtension extension = extensionList[j];
                    synchronizerInstance.registExtension(extension);
                }
                wfElementInstanceMap.Add(synchronizer.Id, synchronizerInstance);
            }

            //结束节点
            List <EndNode> endNodes = workflowProcess.EndNodes;

            //        List<EndNodeInstance> endNodeInstances = netInstance.getEndNodeInstances();
            for (int i = 0; i < endNodes.Count; i++)
            {
                EndNode         endNode         = endNodes[i];
                EndNodeInstance endNodeInstance = new EndNodeInstance(endNode);
                //            endNodeInstances.add(endNodeInstance);
                extensionList = kenelExtensions[endNodeInstance.ExtensionTargetName];
                for (int j = 0; extensionList != null && j < extensionList.Count; j++)
                {
                    IKernelExtension extension = extensionList[j];
                    endNodeInstance.registExtension(extension);
                }
                wfElementInstanceMap.Add(endNode.Id, endNodeInstance);
            }

            //转移线
            List <Transition> transitions = workflowProcess.Transitions;

            for (int i = 0; i < transitions.Count; i++)
            {
                Transition         transition         = (Transition)transitions[i];
                TransitionInstance transitionInstance = new TransitionInstance(transition);

                String fromNodeId = transition.FromNode.Id;
                if (fromNodeId != null)
                {
                    INodeInstance enteringNodeInstance = (INodeInstance)wfElementInstanceMap[fromNodeId];
                    if (enteringNodeInstance != null)
                    {
                        enteringNodeInstance.AddLeavingTransitionInstance(transitionInstance);
                        transitionInstance.EnteringNodeInstance = enteringNodeInstance;
                    }
                }

                String toNodeId = transition.ToNode.Id;
                if (toNodeId != null)
                {
                    INodeInstance leavingNodeInstance = (INodeInstance)wfElementInstanceMap[toNodeId];
                    if (leavingNodeInstance != null)
                    {
                        leavingNodeInstance.AddEnteringTransitionInstance(transitionInstance);
                        transitionInstance.LeavingNodeInstance = leavingNodeInstance;
                    }
                }
                extensionList = kenelExtensions[transitionInstance.ExtensionTargetName];
                for (int j = 0; extensionList != null && j < extensionList.Count; j++)
                {
                    IKernelExtension extension = extensionList[j];
                    transitionInstance.registExtension(extension);
                }
                wfElementInstanceMap.Add(transitionInstance.Id, transitionInstance);
            }

            //循环线
            List <Loop> loops = workflowProcess.Loops;

            for (int i = 0; i < loops.Count; i++)
            {
                Loop         loop         = (Loop)loops[i];
                LoopInstance loopInstance = new LoopInstance(loop);

                String fromNodeId = loop.FromNode.Id;
                if (fromNodeId != null)
                {
                    INodeInstance enteringNodeInstance = (INodeInstance)wfElementInstanceMap[fromNodeId];
                    if (enteringNodeInstance != null)
                    {
                        enteringNodeInstance.AddLeavingLoopInstance(loopInstance);
                        loopInstance.EnteringNodeInstance = enteringNodeInstance;
                    }
                }

                String toNodeId = loop.ToNode.Id;
                if (toNodeId != null)
                {
                    INodeInstance leavingNodeInstance = (INodeInstance)wfElementInstanceMap[toNodeId];
                    if (leavingNodeInstance != null)
                    {
                        leavingNodeInstance.AddEnteringLoopInstance(loopInstance);
                        loopInstance.LeavingNodeInstance = leavingNodeInstance;
                    }
                }
                extensionList = kenelExtensions[loopInstance.ExtensionTargetName];
                for (int j = 0; extensionList != null && j < extensionList.Count; j++)
                {
                    IKernelExtension extension = extensionList[j];
                    loopInstance.registExtension(extension);
                }
                wfElementInstanceMap.Add(loopInstance.Id, loopInstance);
            }
        }
Exemplo n.º 20
0
 public void Connect(ref InputSocket input, out INodeInstance connection)
 {
     connection = null;
 }
Exemplo n.º 21
0
 public void Connect(ref InputSocket input, out INodeInstance connection)
 {
     connection = removeNodes[input.TargetId];
 }
Exemplo n.º 22
0
 public abstract void Setup(IGraphInstance graph, INodeInstance metadata, Actor target);
Exemplo n.º 23
0
 public ConnectionSubscription(INodeInstance node)
 {
     Node      = node;
     Callbacks = new List <Action>();
 }
Exemplo n.º 24
0
 public EventInput(INodeInstance parent, IConnection connection)
 {
     Parent     = parent;
     Connection = connection;
 }
Exemplo n.º 25
0
 public Input(INodeInstance parent, IConnection connection)
 {
     Parent     = parent;
     Connection = (IConnection <T>)connection;
 }
Exemplo n.º 26
0
 public InputSource(Node node, INodeInstance instance, OutputMap outputMapping)
 {
     Node              = node;
     Instance          = instance ?? throw new ArgumentNullException(nameof(instance));
     OutputInformation = outputMapping;
 }
Exemplo n.º 27
0
 public void Unsubscribe(INodeInstance node, Action callback) =>
 Source.Unsubscribe(node, callback);
Exemplo n.º 28
0
 public abstract OutputMap[] Outputs(IGraphConnections graph, INodeInstance instance);
Exemplo n.º 29
0
 internal GraphInstanceNode(INodeInstance instance, InputMap[] inputs, OutputMap[] outputs)
 {
     Instance = instance;
     Inputs   = inputs;
     Outputs  = outputs;
 }
Exemplo n.º 30
0
 public void RegisterInput(INodeInstance node) => Source.RegisterInput(node);