module Fox
Constants
- Context
- Poller
- SockPath
- VERSION
Public Class Methods
_assert(raise_p, req, *dependencies)
click to toggle source
Connects to Fox
server via ZeroMQ and ensures that all requested dependencies are met. If something isn't met, raises a special exception that's rescued by the main run loop and turned into an abort message.
# File lib/keminglabs-fox-rubby.rb, line 21 def self._assert(raise_p, req, *dependencies) deps = dependencies.flatten.uniq.compact return true if deps.empty? sock = Context.socket(ZMQ::REQ) sock.connect req[:socket] sock.send_string JSON.generate({target: req[:target], dependencies: deps}) res = "" sock.recv_string res if (res == "fox-abort") if raise_p raise Abort else false end else true end end
assert(req, *dependencies)
click to toggle source
# File lib/keminglabs-fox-rubby.rb, line 44 def self.assert(req, *dependencies) self._assert true, req, dependencies end
register(path, handler)
click to toggle source
# File lib/keminglabs-fox-rubby.rb, line 49 def self.register(path, handler) FileUtils.mkdir_p SockPath + "/" + File.dirname(path) sock = Context.socket(ZMQ::ROUTER) sock.bind "ipc://#{SockPath}/#{path}.ipc" @handlers[sock] = {handler: handler, path: path} nil end
start!()
click to toggle source
# File lib/keminglabs-fox-rubby.rb, line 58 def self.start! @handlers.each do |sock, h| $stderr.puts "Registering handler at: #{h[:path]}" Poller.register_readable sock end Signal.trap("INT") do break Context.terminate end loop do Poller.poll(:blocking) Poller.readables.each do |sock| id, req = recv_multipart sock msg = begin parse_handler_response @handlers[sock][:handler].call(req) rescue Abort => _ {exit: "abort"} rescue Exception => e $stderr.puts e {exit: "fail", log: e.to_s} end $stderr.puts "#{msg[:exit]}: #{req[:target]}" send! sock, id, msg end end end
Private Class Methods
parse_handler_response(res)
click to toggle source
# File lib/keminglabs-fox-rubby.rb, line 105 def self.parse_handler_response(res) case res when String # a successful build { exit: "succeed", result: res } when Array # a successful build with log messages { exit: "succeed", result: res[0], log: res[1] } when Hash # a full map if not (res.key?(:exit) or res.key?("exit")) throw "Response needs :exit key with value one of (:succeed, :abort, :fail)" end res end end
recv_multipart(sock)
click to toggle source
# File lib/keminglabs-fox-rubby.rb, line 96 def self.recv_multipart(sock) parts = [] sock.recvmsgs parts id, _, msg = parts [id.copy_out_string, JSON.parse(msg.copy_out_string, symbolize_names: true)] end
send!(sock, id, msg)
click to toggle source
TODO: do I really want to make things private? This is just a documentation issue, really.
# File lib/keminglabs-fox-rubby.rb, line 92 def self.send!(sock, id, msg) sock.send_strings [id, "", JSON.generate(msg)] end