Advertisement
FluttyProger

Bridge.lua

Nov 19th, 2016
98
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 3.93 KB | None | 0 0
  1. local HOST = "bridge.computercraft.ru:1111"
  2. local commandIdent = "+#"
  3. local deviceCommandIdent = "+$"
  4. local internet
  5. local socket, connectedToBridge, connectedToDevice, KEY
  6. local msgBuffer = {}
  7. local BR = {}
  8.  
  9. function BR.split(source, delimiters)
  10.   local elements = {}
  11.   local pattern = '([^'..delimiters..']+)'
  12.   string.gsub(source, pattern, function(value) elements[#elements + 1] =     value;  end);
  13.   return elements
  14. end
  15.  
  16. local function tableToJSON(arr)
  17.   local json = "{"
  18.   local delim = ""
  19.   for k, v in pairs(arr) do
  20.     json = json .. delim .."\"" .. tostring(k) .. "\":\"" .. tostring(v) .. "\""
  21.     delim = ","
  22.   end
  23.   json = json.."}"
  24.   return json
  25. end
  26.  
  27. local function enqueue(array, n)
  28.   n = n or 1
  29.   for i = n, #array do
  30.     table.insert(msgBuffer, array[i])
  31.   end
  32. end
  33.  
  34. local function sendInternal(str)
  35.   if not str or str == "" then return false end
  36.   local data = str.."\0"
  37.   local buff
  38.   local i = 0
  39.   while i < 4 do
  40.     buff = socket.write(data)
  41.     if not buff then
  42.       connectedToBridge = false
  43.       return false
  44.     elseif buff > 0 then
  45.       return true
  46.     end
  47.     -- RETRY IF BUFF IS 0
  48.     i = i + 1
  49.   end
  50.  
  51.   return true  
  52. end
  53.  
  54.  
  55. function BR.isBridgeConnected() return connectedToBridge end
  56. function BR.isPairConnected() return connectedToDevice end
  57.  
  58. function BR.sendNotification(notif)
  59.   sendInternal(deviceCommandIdent .. "31 " .. tableToJSON(notif))
  60. end
  61.  
  62. function BR.sendToast(text, duration)
  63.   duration = duration or 0
  64.   sendInternal(deviceCommandIdent .. "30 " .. tostring(duration) .. " " .. text)
  65. end
  66.  
  67. function BR.send(str)
  68.   if not str or str == "" then return false end
  69.   return sendInternal("-"..str)
  70. end
  71.  
  72. local function execCommand(cmd)
  73.   local cmdNum = string.sub(cmd, 3, 4)
  74.  
  75.   if     cmdNum == "00" then
  76.     --ping
  77.     sendInternal(string.sub(cmd, 1, 2) .. "01") --REPLY TO SENDER
  78.   elseif cmdNum == "01" then
  79.     --pong
  80.   elseif cmdNum == "02" then
  81.     connectedToBridge = false
  82.     --bridge stopped
  83.   elseif cmdNum == "10" then
  84.     connectedToDevice = false
  85.     --no pair
  86.   elseif cmdNum == "20" then
  87.     connectedToDevice = true
  88.     --pair found
  89.   elseif cmdNum == "21" then
  90.     connectedToDevice = false
  91.   end
  92. end
  93.  
  94. local function isCommand(str)
  95.   if string.sub(str, 1, 1) == "+" then
  96.     return true
  97.   end
  98.   return false
  99. end
  100.  
  101. function BR.receive()
  102.   local buff
  103.   if connectedToBridge then
  104.     buff = socket.read()
  105.     if buff == nil then --CONNECTION LOST
  106.       connectedToBridge = false
  107.       connectedToDevice = false
  108.       return nil, false
  109.     elseif #msgBuffer > 0 then --IF BUFFER HAS DATA
  110.       if buff ~= "" then --IF MESSAGE IS NOT EMPTY
  111.         enqueue(BR.split(buff, "\0"))
  112.       end
  113.  
  114.       buff = table.remove(msgBuffer, 1) --GET FIRST MESSAGE FROM BUFFER
  115.     elseif buff == "" then
  116.       return buff, connectedToDevice
  117.     end
  118.  
  119.     local m = BR.split(buff, "\0")
  120.     if #m > 1 then
  121.       enqueue(m, 2)
  122.       buff = m[1]
  123.     end
  124.  
  125.     while true do
  126.       if isCommand(buff) then
  127.         execCommand(buff)
  128.         --return "", connectedToDevice
  129.         if(#msgBuffer > 0) then
  130.           buff = table.remove(msgBuffer, 1)
  131.         else
  132.           return "", connectedToDevice
  133.         end
  134.       else
  135.         buff = BR.split(buff, "\0")[1] --CUT \0
  136.         if buff == nil then return "", connectedToDevice end  
  137.         return string.sub(buff, 2, #buff), connectedToDevice
  138.       end
  139.     end
  140.   end    
  141.   return nil, false
  142. end
  143.  
  144. function BR.init(key, newHost)
  145.   if not key or key == "" then return false end
  146.   KEY = key
  147.   HOST = newHost or HOST
  148.   internet = require("component").internet
  149.   socket = internet.connect(HOST)
  150.   if not socket then return false end
  151.   local i = 0
  152.   while not socket.finishConnect() do
  153.     if i >= 4 then
  154.       return false
  155.     end
  156.     i = i + 1
  157.     os.sleep(0.1)
  158.   end
  159.  
  160.   sendInternal("KOC-"..key)
  161.   connectedToDevice = false
  162.   connectedToBridge = true
  163.   return true
  164. end
  165.  
  166. return BR
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement