From 979a6d8674b33cfb590786618748e1430be126a8 Mon Sep 17 00:00:00 2001 From: Ryan Ward Date: Mon, 25 Jun 2018 21:25:59 -0400 Subject: [PATCH] Node manager working A few things are left to do. Queues and adding support for some of the system threaded objects that exist. --- changes.md | 78 +++++++++++++++++++++++++++- multi/integration/networkManager.lua | 7 ++- node.lua | 10 ++-- nodeManager.lua | 3 +- test.lua | 52 +++++++++---------- 5 files changed, 112 insertions(+), 38 deletions(-) diff --git a/changes.md b/changes.md index 461a61c..ba28777 100644 --- a/changes.md +++ b/changes.md @@ -6,8 +6,82 @@ Update: 2.0.0 Big update #Added: - require("multi.integration.networkManager") -- multi:newNode([name]) -- multi:newMaster(name) +- multi:newNode(tbl: settings) +- multi:newMaster(tbl: settings) +- multi:nodeManager(port) + +Note: These examples assume that you have already connected the nodes to the node manager. Also you do not need to use the node manager, but sometimes broadcast does not work as expected and the master doesnot connect to the nodes. Using the node manager offers nice features like: removing nodes from the master when they have disconnected, and automatically telling the master when nodes have been added. + +**NodeManager.lua** +```lua + +``` + +**Node.lua** +```lua +package.path="?/init.lua;?.lua;"..package.path +multi = require("multi") +local GLOBAL, THREAD = require("multi.integration.lanesManager").init() +nGLOBAL = require("multi.integration.networkManager").init() +master = multi:newNode{ + crossTalk = false, -- default value, allows nodes to talk to eachother. WIP NOT READY YET! + allowRemoteRegistering = true, -- allows you to register functions from the master on the node, default is false + name = nil, -- default value + noBroadCast = true, -- if using the node manager, set this to true to prevent the node from broadcasting + managerDetails = {"localhost",12345}, -- connects to the node manager if one exists +} +function RemoteTest(a,b,c) -- a function that we will be executing remotely + print("Yes I work!",a,b,c) +end +settings = { + priority = 0, -- 1 or 2 + protect = false, -- if something goes wrong we will crash hard, but the speed gain is good +} +multi:mainloop(settings) +``` + +**Master.lua** +```lua +-- set up the package +package.path="?/init.lua;?.lua;"..package.path +-- Import the libraries +multi = require("multi") +local GLOBAL, THREAD = require("multi.integration.lanesManager").init() +nGLOBAL = require("multi.integration.networkManager").init() +-- Act as a master node +master = multi:newMaster{ + name = "Main", -- the name of the master + noBroadCast = true, -- if using the node manager, set this to true to avoid double connections + managerDetails = {"localhost",12345}, -- the details to connect to the node manager (ip,port) +} +-- Send to all the nodes that are connected to the master +master:doToAll(function(node_name) + master:register("TestFunc",node_name,function(msg) + print("It works: "..msg) + end) + multi:newAlarm(2):OnRing(function(alarm) + master:execute("TestFunc",node_name,"Hello!") + alarm:Destroy() + end) + multi:newThread("Checker",function() + while true do + thread.sleep(1) + if nGLOBAL["test"] then + print(nGLOBAL["test"]) + thread.kill() + end + end + end) + nGLOBAL["test2"]={age=22} +end) + +-- Starting the multitasker +settings = { + priority = 0, -- 0, 1 or 2 + protect = false, +} +multi:mainloop(settings) +``` **Note:** There are many ways to work this. You could send functions/methods to a node like haw systemThreadedJobQueue work. Or you could write the methods you want in advance in each node file and send over the command to run the method with arguments ... and it will return the results. Network threading is different than system threading. Data transfer is really slow compared to system threading. In fact the main usage for this feature in the library is mearly for experments. Right now I honestly do not know what I want to do with this feature and what I am going to add to this feature. The ablitiy to use this frature like a system thread will be possible, but there are some things that differ. diff --git a/multi/integration/networkManager.lua b/multi/integration/networkManager.lua index 3ffdb9c..dc0cc90 100644 --- a/multi/integration/networkManager.lua +++ b/multi/integration/networkManager.lua @@ -31,13 +31,16 @@ end -- Internal queue system for network queues local queue = {} queue.__index = queue -function queue:newQueue() +function queue:newQueue(name,master) + if not name then error("You must include a name in order to create a queue!") end local c = {} + c.name = name + c.master = master setmetatable(c,self) return c end function queue:push(data) - table.insert(self,packData(data)) + master:doToAll(char(CMD_QUEUE)..packData(data)) end function queue:raw_push(data) -- Internal usage only table.insert(self,data) diff --git a/node.lua b/node.lua index 1a63439..3f2239a 100644 --- a/node.lua +++ b/node.lua @@ -3,17 +3,17 @@ multi = require("multi") local GLOBAL, THREAD = require("multi.integration.lanesManager").init() nGLOBAL = require("multi.integration.networkManager").init() master = multi:newNode{ - crossTalk = false, -- default value - allowRemoteRegistering = true, + crossTalk = false, -- default value, allows nodes to talk to eachother. WIP NOT READY YET! + allowRemoteRegistering = true, -- allows you to register functions from the master on the node, default is false name = nil, -- default value - noBroadCast = true, + noBroadCast = true, -- if using the node manager, set this to true to prevent the node from broadcasting managerDetails = {"localhost",12345}, -- connects to the node manager if one exists } -function RemoteTest(a,b,c) +function RemoteTest(a,b,c) -- a function that we will be executing remotely print("Yes I work!",a,b,c) end settings = { priority = 0, -- 1 or 2 - protect = false, + protect = false, -- if something goes wrong we will crash hard, but the speed gain is good } multi:mainloop(settings) diff --git a/nodeManager.lua b/nodeManager.lua index d520b0c..7d57596 100644 --- a/nodeManager.lua +++ b/nodeManager.lua @@ -2,10 +2,11 @@ package.path="?/init.lua;?.lua;"..package.path multi = require("multi") local GLOBAL, THREAD = require("multi.integration.lanesManager").init() nGLOBAL = require("multi.integration.networkManager").init() -multi:nodeManager(12345) +multi:nodeManager(12345) -- Host a node manager on port: 12345 print("Node Manager Running...") settings = { priority = 0, -- 1 or 2 protect = false, } multi:mainloop(settings) +-- Thats all you need to run the node manager, everything else is done automatically diff --git a/test.lua b/test.lua index 26bacc0..9a8a58a 100644 --- a/test.lua +++ b/test.lua @@ -6,38 +6,34 @@ local GLOBAL, THREAD = require("multi.integration.lanesManager").init() nGLOBAL = require("multi.integration.networkManager").init() -- Act as a master node master = multi:newMaster{ - pollManagerRate = 15, - name = "Main", - noBroadCast = true, - managerDetails = {"localhost",12345}, + name = "Main", -- the name of the master + noBroadCast = true, -- if using the node manager, set this to true to avoid double connections + managerDetails = {"localhost",12345}, -- the details to connect to the node manager (ip,port) } +-- Send to all the nodes that are connected to the master +master:doToAll(function(node_name) + master:register("TestFunc",node_name,function(msg) + print("It works: "..msg) + end) + multi:newAlarm(2):OnRing(function(alarm) + master:execute("TestFunc",node_name,"Hello!") + alarm:Destroy() + end) + multi:newThread("Checker",function() + while true do + thread.sleep(1) + if nGLOBAL["test"] then + print(nGLOBAL["test"]) + thread.kill() + end + end + end) + nGLOBAL["test2"]={age=22} +end) + -- Starting the multitasker settings = { priority = 0, -- 0, 1 or 2 protect = false, } ---~ master.OnFirstNodeConnected(function(node_name) -multi:newAlarm(3):OnRing(function(alarm) - master:doToAll(function(node_name) - master:register("TestFunc",node_name,function(msg) - print("It works: "..msg) - end) - multi:newAlarm(2):OnRing(function(alarm) - master:execute("TestFunc",node_name,"Hello!") - alarm:Destroy() - end) - multi:newThread("Checker",function() - while true do - thread.sleep(1) - if nGLOBAL["test"] then - print(nGLOBAL["test"]) - thread.kill() - end - end - end) - nGLOBAL["test2"]={age=22} - end) - alarm:Destroy() -end) ---~ os.execute("start lua node.lua") multi:mainloop(settings)