module Splib

Constants

LIBS
Suff
bytes

number of bytes

Converts bytes into easy human readable form O(1) version by Ryan “pizza_milkshake” Flynn

Public Class Methods

create_holder(path) click to toggle source
path

path to ruby code

Creates a module to hold loaded code

# File lib/woolen_common/splib/CodeReloader.rb, line 51
def self.create_holder(path)
    return Module.new do
        @path = path
        def self.path
            @path
        end
    end
end
discover_constants(path, type=nil) click to toggle source
path

path to ruby file

type

return constants only of given type

Find all constants in a given ruby file. Array of symbols is returned

# File lib/woolen_common/splib/CodeReloader.rb, line 14
def self.discover_constants(path, type=nil)
    raise ArgumentError.new('Failed to locate plugin file') unless File.exists?(path)
    consts = []
    sandbox = Module.new
    sandbox.module_eval(self.read_file(path))
    sandbox.constants.each do |const|
        klass = sandbox.const_get(const)
        if(type.nil? || (type && klass < type))
            sklass = klass.to_s.slice(klass.to_s.rindex(':')+1, klass.to_s.length)
            consts << sklass.to_sym
        end
    end
    return consts
end
exec(*args) click to toggle source
command

command string to execute

timeout

length of time to execute

maxbytes

maximum number return bytes allowed

Execute system command. This is a wrapper method that will redirect to the proper command

# File lib/woolen_common/splib/Exec.rb, line 22
def self.exec(*args)
    if(RUBY_PLATFORM == 'java')
        thread_exec(*args)
    else
        standard_exec(*args)
    end
end
find_const(c, things=[]) click to toggle source
c

constant name (String)

things

Array of Object/Module constants to look in

Finds a constant if it exists

Example

Foo::Bar

Returns nil if nothing found

# File lib/woolen_common/splib/Constants.rb, line 7
def self.find_const(c, things=[])
    raise ArgumentError.new('Exepcting an array') unless things.is_a?(Array)
    const = nil
    (things + [Object]).each do |base|
        begin
            c.split('::').each do |part|
                const = const.nil? ? base.const_get(part) : const.const_get(part)
            end
        rescue NameError
            const = nil
        end
        break unless const.nil?
    end
    const
end
format_seconds(secs) click to toggle source
secs

number of seconds

Converts seconds into a human readable string (This is an estimate and does not account for leaps)

# File lib/woolen_common/splib/Conversions.rb, line 5
def self.format_seconds(secs)
    arg = [{:year => 31536000},
            {:month => 2678400},
            {:week => 604800},
            {:day => 86400},
            {:hour => 3600},
            {:minute => 60},
            {:second => 1}]
    res = ''
    arg.each do |val|
        val.each_pair do |k,v|
            z = (secs / v).to_i
            next unless z > 0
            res += " #{z} #{k}#{z == 1 ? '':'s'}"
            secs = secs % v
        end
    end
    res = '0 seconds' if res.empty?
    return res.strip
end
format_size(bytes) click to toggle source
# File lib/woolen_common/splib/Conversions.rb, line 40
def self.format_size(bytes)
    return "0 bytes" if bytes == 0
    mag = (Math.log(bytes) / Math.log(1024)).floor
    mag = [ Suff.length - 1, mag ].min
    val = bytes.to_f / (1024 ** mag)
    ("%.2f %sbyte%s" % [ val, Suff[mag], val == 1 ? "" : "s" ]).strip
end
isgd_url(url) click to toggle source
url

URL to shorten

Gets a is.gd for given URL

# File lib/woolen_common/splib/UrlShorteners.rb, line 26
def self.isgd_url(url)
    connection = Net::HTTP.new('is.gd', 80)
    resp, data = connection.get("/api.php?longurl=#{url}")
    if(resp.code !~ /^200$/)
        raise "Failed to make the URL small."
    end
    return data.strip
end
load(*args) click to toggle source
args

name of library to load

Loads the given library. Currently available: :CodeReloader :Constants :Conversions :Exec :HumanIdealRandomIterator :PriorityQueue :UrlShorteners :all

# File lib/woolen_common/splib.rb, line 24
def self.load(*args)
    if args.include?(:all)
        LIBS.each do |lib|
            require File.join(File.dirname(__FILE__), 'splib', lib.to_s)
        end
    else
        args.each do |lib|
            raise NameError.new("Unknown library name: #{lib}") unless LIBS.include?(lib)
            require File.join(File.dirname(__FILE__), 'splib', lib.to_s)
        end
    end
end
load_code(path, holder=nil) click to toggle source
path

path to ruby file

holder

module holding loaded ruby code

Load code from a ruby file into a module

# File lib/woolen_common/splib/CodeReloader.rb, line 32
def self.load_code(path, holder=nil)
    if(holder)
        raise ArgumentError.new('Expecting a module containing loaded code') unless holder.respond_to?(:path)
    else
        holder = self.create_holder(path)
    end
    holder.module_eval(self.read_file(path))
    holder
end
path() click to toggle source
# File lib/woolen_common/splib/CodeReloader.rb, line 54
def self.path
    @path
end
read_file(path) click to toggle source
path

path to file

Read contents of file

# File lib/woolen_common/splib/CodeReloader.rb, line 4
def self.read_file(path)
    file = File.open(path, 'rb')
    cont = file.read
    file.close
    cont
end
reload_code(holder) click to toggle source
holder

module holding loaded ruby code

Reload the code within the module

# File lib/woolen_common/splib/CodeReloader.rb, line 44
def self.reload_code(holder)
    raise ArgumentError.new('Expecting a module containing loaded code') unless holder.respond_to?(:path)
    self.load_code(holder.path)
end
running_procs() click to toggle source

Returns current array of running Processes

# File lib/woolen_common/splib/Exec.rb, line 14
def self.running_procs
    @@processes
end
shortest_url(url) click to toggle source
url

URL to shorten

Get shortest for given url

# File lib/woolen_common/splib/UrlShorteners.rb, line 36
def self.shortest_url(url)
    results = []
    [:tiny_url, :isgd_url, :trim_url].each do |service|
        begin
            results << self.send(service, url)
        rescue
            #ignore#
        end
    end
    raise 'Failed to make URL small' if results.empty?
    results.sort{|a,b| a.length <=> b.length}[0]
end
sleep(secs=nil) click to toggle source
secs

Number of seconds to sleep (Use float to provide better actual sleep time)

# File lib/woolen_common/splib/Sleep.rb, line 4
def sleep(secs=nil)
    start = Time.now.to_f
    secs.nil? ? Kernel.sleep : Kernel.sleep(secs)
    Time.now.to_f - start
end
standard_exec(command, timeout=10, maxbytes=500, priority=nil) click to toggle source
command

command to execute

timeout

maximum number of seconds to run

maxbytes

maximum number of result bytes to accept

priority

set priority of the process

Execute a system command (use with care) This is the normal exec command that is used

# File lib/woolen_common/splib/Exec.rb, line 36
def self.standard_exec(command, timeout=10, maxbytes=500, priority=nil)
    timeout = timeout.to_i
    maxbytes = maxbytes.to_i
    priority = priority.to_i
    output = []
    pro = nil
    begin
        if(timeout > 0)
            Timeout::timeout(timeout) do
                pro = IO.popen(command)
                @@processes << pro
                if(priority > 0)
                    Process.setpriority(Process::PRIO_PROCESS, pro.pid, priority)
                end
                until(pro.closed? || pro.eof?)
                    output << pro.getc.chr
                    if(maxbytes > 0 && output.size > maxbytes)
                        raise IOError.new("Maximum allowed output bytes exceeded. (#{maxbytes} bytes)")
                    end
                end
            end
        else
            pro = IO.popen(command)
            @@processes << pro
            until(pro.closed? || pro.eof?)
                output << pro.getc.chr
                if(maxbytes > 0 && output.size > maxbytes)
                    raise IOError.new("Maximum allowed output bytes exceeded. (#{maxbytes} bytes)")
                end
            end
        end
        output = output.join('')
    ensure
        Process.kill('KILL', pro.pid) if Process.waitpid2(pro.pid, Process::WNOHANG).nil? # make sure the process is dead
        @@processes.delete(pro)
    end
    return output
end
thread_exec(command, timeout=10, maxbytes=500) click to toggle source
command

command to execute

timeout

maximum number of seconds to run

maxbytes

maximum number of result bytes to accept

priority

set priority of the process

Execute a system command (use with care) This is the threaded exec command that is generally used with JRuby. The regular timeout does not work when executing a process, so we do it in a separate thread and sleep the main thread until the timeout is reached.

# File lib/woolen_common/splib/Exec.rb, line 87
def self.thread_exec(command, timeout=10, maxbytes=500)
    timeout = timeout.to_i
    maxbytes = maxbytes.to_i
    priority = priority.to_i
    current = Thread.current
    output = []
    pro = nil
    thread = Thread.new do
        boom = Complete.new
        begin
            pro = IO.popen(command)
            @@processes << pro
            if(priority > 0)
                Process.setpriority(Process::PRIO_PROCESS, pro.pid, priority)
            end
            until(pro.closed? || pro.eof?)
                output << pro.getc.chr
                if(maxbytes > 0 && output.size > maxbytes)
                    raise IOError.new("Maximum allowed output bytes exceeded. (#{maxbytes} bytes)")
                end
            end
        rescue Exception => boom
            # just want it set
        end
        current.raise boom unless boom.is_a?(Timeout::Error)
    end
    begin
        begin
            if(timeout > 0)
                thread.join(timeout)
                thread.raise Timeout::Error.new
                raise Timeout::Error.new
            else
                thread.join
            end
            output.join('')
        rescue Complete
            # ignore this exception
        end
    ensure
        Process.kill('KILL', pro.pid) unless pro.nil?
        @@processes.delete(pro)
    end
    output.join('')
end
tiny_url(url) click to toggle source
url

URL to shorten

Gets a tinyurl for given URL

# File lib/woolen_common/splib/UrlShorteners.rb, line 6
def self.tiny_url(url)
    connection = Net::HTTP.new('tinyurl.com', 80)
    resp, data = connection.get("/api-create.php?url=#{url}")
    if(resp.code !~ /^200$/)
        raise "Failed to make the URL small."
    end
    return data.strip
end
trim_url(url) click to toggle source
url

URL to shorten

Gets a tr.im for given URL

# File lib/woolen_common/splib/UrlShorteners.rb, line 16
def self.trim_url(url)
    connection = Net::HTTP.new('api.tr.im', 80)
    resp, data = connection.get("/v1/trim_simple?url=#{url}")
    if(resp.code !~ /^200$/)
        raise "Failed to make the URL small."
    end
    return data.strip
end
type_of?(a, b) click to toggle source
a

an object

b

constant or string

Returns true of a is a type of b. b can be given as a String to allow for matching of types contained within a module or for types that may not be loaded

# File lib/woolen_common/splib/Constants.rb, line 28
def self.type_of?(a, b)
    case b
    when String
        if(a.class.to_s.slice(0).chr == '#')
            name = a.class.to_s
            return name.slice(name.index('::')+2, name.length) == b
        else
            const = self.find_const(b)
            return const.nil? ? false : a.is_a?(const)
        end
    when Class
        return a.is_a?(b)
    else
        raise ArgumentError.new('Comparision type must be a string or constant')
    end
end