rex 0.0.4
Sign up to get free protection for your applications and to get access to all the features.
- data/README +50 -0
- data/lib/rex.rb +23 -0
- data/lib/rex/array.rb +13 -0
- data/lib/rex/kernel.rb +11 -0
- data/lib/rex/modules/boolean.rb +14 -0
- data/lib/rex/modules/caller_name.rb +15 -0
- data/lib/rex/modules/ordinal.rb +35 -0
- data/lib/rex/modules/propercase.rb +15 -0
- data/lib/rex/modules/roman.rb +41 -0
- data/lib/rex/modules/scrub.rb +66 -0
- data/lib/rex/modules/stacktrace.rb +31 -0
- data/lib/rex/modules/swap.rb +13 -0
- data/lib/rex/modules/to_proc.rb +13 -0
- data/lib/rex/modules/tuple.rb +14 -0
- data/lib/rex/modules/wrap.rb +15 -0
- data/lib/rex/numeric.rb +19 -0
- data/lib/rex/string.rb +21 -0
- data/lib/rex/symbol.rb +13 -0
- data/test/boolean.rb +64 -0
- data/test/caller_name.rb +26 -0
- data/test/ordinal.rb +609 -0
- data/test/propercase.rb +40 -0
- data/test/roman.rb +335 -0
- data/test/scrub.rb +27 -0
- data/test/stacktrace.rb +24 -0
- data/test/swap.rb +44 -0
- data/test/to_proc.rb +24 -0
- data/test/tuple.rb +26 -0
- data/test/wrap.rb +44 -0
- metadata +92 -0
data/README
ADDED
@@ -0,0 +1,50 @@
|
|
1
|
+
== What
|
2
|
+
Ruby Extension Library version 0.0.4
|
3
|
+
|
4
|
+
This is a collection of Ruby class monkeypatches. Some of these are by me and
|
5
|
+
some have been swiped from other places. I have no shame.
|
6
|
+
|
7
|
+
== How
|
8
|
+
require 'rubygems'
|
9
|
+
require 'rex'
|
10
|
+
|
11
|
+
Stuff you get:
|
12
|
+
Array#swap!(a, b)
|
13
|
+
File#random_line(separator="#{$/}", seed=nil)
|
14
|
+
Integer#to_ordinal
|
15
|
+
Integer#from_ordinal(ordinal)
|
16
|
+
Integer#to_roman
|
17
|
+
Integer#from_roman(roman)
|
18
|
+
Kernel#boolean?
|
19
|
+
Kernel#caller_name
|
20
|
+
Kernel#stack_trace(msg=nil)
|
21
|
+
Kernel#Tuple(*ary)
|
22
|
+
String#propercase
|
23
|
+
String#scrub!(allowed=BASIC_MARKUP)
|
24
|
+
String#wrap(columns=78)
|
25
|
+
Symbol#to_proc
|
26
|
+
|
27
|
+
You can run the example programs in the examples directory to see what the
|
28
|
+
above methods do. You can run the example programs from anywhere, e.g.:
|
29
|
+
|
30
|
+
ruby ~/src/projects/rex/examples/stacktrace.rb
|
31
|
+
|
32
|
+
== Install
|
33
|
+
To construct a Ruby gem, just type:
|
34
|
+
|
35
|
+
rake gem
|
36
|
+
|
37
|
+
To install it, type:
|
38
|
+
|
39
|
+
sudo gem install pkg/rex-0.0.4.gem
|
40
|
+
|
41
|
+
== Notes
|
42
|
+
I haven't tested this code with YARV, so YMMV.
|
43
|
+
|
44
|
+
Symbol#to_proc comes from the blog post:
|
45
|
+
http://weblog.raganwald.com/2008/02/1100inject.html
|
46
|
+
|
47
|
+
== Contribute
|
48
|
+
The source is availble at github: git://github.com/yesmar/rex.git. Feel free
|
49
|
+
to clone it and implement your own awesome ideas. You can also send your
|
50
|
+
patches by email to yesmar[at]speakeasy[dot]net.
|
data/lib/rex.rb
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# rex.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module REX
|
7
|
+
REX::NAME = 'rex'
|
8
|
+
REX::VERSION = '0.0.4'
|
9
|
+
REX::COPYRIGHT = 'Copyright (c) 2008 Ramsey Dow'
|
10
|
+
def self.copyright() REX::COPYRIGHT end
|
11
|
+
def self.version() REX::VERSION end
|
12
|
+
def self.libdir() File.expand_path(__FILE__).gsub(%r/\.rb$/, '') end
|
13
|
+
end
|
14
|
+
|
15
|
+
$LOAD_PATH.unshift(File.dirname(__FILE__)+'/rex')
|
16
|
+
|
17
|
+
require 'array'
|
18
|
+
require 'kernel'
|
19
|
+
require 'numeric'
|
20
|
+
require 'string'
|
21
|
+
require 'symbol'
|
22
|
+
|
23
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
data/lib/rex/array.rb
ADDED
data/lib/rex/kernel.rb
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# boolean.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Kernel
|
7
|
+
def boolean?
|
8
|
+
raise ArgumentError, 'nil self' if self.nil?
|
9
|
+
|
10
|
+
self.class == TrueClass || self.class == FalseClass
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,15 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# caller_name.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Kernel
|
7
|
+
def caller_name
|
8
|
+
k = caller[0].split(%r{:[\d]*:in})
|
9
|
+
return k[0] if !k.nil? && !k.empty?
|
10
|
+
|
11
|
+
nil
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,35 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# ordinal.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Ordinal
|
7
|
+
# convert number to ordinal
|
8
|
+
def to_ordinal
|
9
|
+
cardinal = self.to_i.abs
|
10
|
+
if (10...20).include?(cardinal) then
|
11
|
+
cardinal.to_s << 'th'
|
12
|
+
else
|
13
|
+
cardinal.to_s << %w{th st nd rd th th th th th th}[cardinal % 10]
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
# convert ordinal to number
|
18
|
+
def Integer.from_ordinal(ordinal)
|
19
|
+
raise ArgumentError, 'nil ordinal' if ordinal.nil?
|
20
|
+
raise ArgumentError, 'invalid ordinal class' if ordinal.class != String
|
21
|
+
raise ArgumentError, 'empty ordinal' if ordinal.empty?
|
22
|
+
raise ArgumentError, 'not an ordinal' if ordinal.length < 3
|
23
|
+
|
24
|
+
suffix = ordinal[-2,2]
|
25
|
+
if suffix == 'st' || suffix == 'nd' || suffix == 'rd' || suffix == 'th'
|
26
|
+
value = ordinal[0,ordinal.length-2]
|
27
|
+
else
|
28
|
+
raise 'not an ordinal'
|
29
|
+
end
|
30
|
+
|
31
|
+
value.to_i
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,15 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# propercase.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module ProperCase
|
7
|
+
# convert string to Proper Case
|
8
|
+
def propercase
|
9
|
+
ary = self.split(' ')
|
10
|
+
ary.each { |e| e.capitalize! }
|
11
|
+
ary.join(' ')
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,41 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# roman.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Roman
|
7
|
+
ROMAN_NUMERALS = [ ['M', 1000], ['CM', 900], ['D', 500],
|
8
|
+
['CD', 400], ['C', 100], ['XC', 90], ['L', 50], ['XL', 40],
|
9
|
+
['X', 10], ['IX', 9], ['V', 5], ['IV', 4], ['I', 1] ]
|
10
|
+
|
11
|
+
# convert Integer to Roman numeral
|
12
|
+
def to_roman
|
13
|
+
remainder = self
|
14
|
+
roman = ''
|
15
|
+
for sym,sum in ROMAN_NUMERALS
|
16
|
+
while remainder >= sum
|
17
|
+
remainder -= sum
|
18
|
+
roman << sym
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
roman
|
23
|
+
end
|
24
|
+
|
25
|
+
# convert Roman numeral to Integer
|
26
|
+
def Integer.from_roman(roman)
|
27
|
+
str = roman.upcase
|
28
|
+
sum = 0
|
29
|
+
for entry in ROMAN_NUMERALS
|
30
|
+
sym,num = entry[0], entry[1]
|
31
|
+
while sym == str[0, sym.length]
|
32
|
+
sum += num
|
33
|
+
str.slice!(0, sym.length)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
sum
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,66 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# scrub.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Scrub
|
7
|
+
# dictionary of allowable HTML tags and attributes
|
8
|
+
BASIC_MARKUP = {
|
9
|
+
'a' => ['href', 'title'],
|
10
|
+
'img' => ['src', 'alt', 'title'],
|
11
|
+
'br' => [],
|
12
|
+
'i' => nil,
|
13
|
+
'u' => nil,
|
14
|
+
'b' => nil,
|
15
|
+
'pre' => nil,
|
16
|
+
'kbd' => nil,
|
17
|
+
'code' => ['lang'],
|
18
|
+
'cite' => nil,
|
19
|
+
'strong' => nil,
|
20
|
+
'em' => nil,
|
21
|
+
'ins' => nil,
|
22
|
+
'sup' => nil,
|
23
|
+
'del' => nil,
|
24
|
+
'table' => nil,
|
25
|
+
'tr' => nil,
|
26
|
+
'td' => nil,
|
27
|
+
'th' => nil,
|
28
|
+
'ol' => nil,
|
29
|
+
'ul' => nil,
|
30
|
+
'li' => nil,
|
31
|
+
'p' => nil,
|
32
|
+
'h1' => nil,
|
33
|
+
'h2' => nil,
|
34
|
+
'h3' => nil,
|
35
|
+
'h4' => nil,
|
36
|
+
'h5' => nil,
|
37
|
+
'h6' => nil,
|
38
|
+
'blockquote' => ['cite']
|
39
|
+
}
|
40
|
+
|
41
|
+
# TODO: add option to replace scrubbed text with a user-defined tag
|
42
|
+
def scrub!(allowed=BASIC_MARKUP)
|
43
|
+
gsub!(/<(\/*)(\w+)([^>]*)>/) do
|
44
|
+
raw = $~
|
45
|
+
tag = raw[2].downcase
|
46
|
+
if allowed.has_key? tag
|
47
|
+
pcs = [tag]
|
48
|
+
allowed[tag].each do |prop|
|
49
|
+
['"', "'", ''].each do |q|
|
50
|
+
q2 = (q != '' ? q : '\s')
|
51
|
+
if raw[3] =~ /#{prop}\s*=\s*#{q}([^#{q2}]+)#{q}/i
|
52
|
+
pcs << "#{prop}=\"#{$1.gsub('"', '\\"')}\""
|
53
|
+
break
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end if allowed[tag]
|
57
|
+
"<#{raw[1]}#{pcs.join ' '}>"
|
58
|
+
else
|
59
|
+
''
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
end
|
65
|
+
|
66
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,31 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# stacktrace.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Kernel
|
7
|
+
SPONSOR = 'yesmar'
|
8
|
+
|
9
|
+
def stacktrace(msg=nil)
|
10
|
+
raise ArgumentError, 'invalid msg class' if msg.class != String if !msg.nil?
|
11
|
+
|
12
|
+
program = File.basename(caller_name) || 'unknown'
|
13
|
+
st = []
|
14
|
+
|
15
|
+
st << "#{msg} " if !msg.nil? && !msg.empty?
|
16
|
+
st << 'Stack Trace:'
|
17
|
+
|
18
|
+
i = 1
|
19
|
+
caller.each do |c|
|
20
|
+
st << " #{c}"
|
21
|
+
i += 1
|
22
|
+
if i == caller.size-1
|
23
|
+
st << " #{program}:this stack trace is brought to you by #{SPONSOR}"
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
st
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,13 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# to_proc.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module ToProc
|
7
|
+
# turn symbol into a simple proc
|
8
|
+
def to_proc
|
9
|
+
Proc.new { |*args| args.shift.__send__(self, *args) }
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,14 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# tuple.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Kernel
|
7
|
+
def Tuple(*ary)
|
8
|
+
ary = ary[0] if ary.size == 1 and ary[0].kind_of?(Enumerable)
|
9
|
+
ary = ary.to_a unless ary.kind_of?(Array)
|
10
|
+
ary.extend Comparable
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
@@ -0,0 +1,15 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# wrap.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
module Wrap
|
7
|
+
DEFAULT_COLUMNS=78
|
8
|
+
|
9
|
+
# variable-length word wrap
|
10
|
+
def wrap(columns=DEFAULT_COLUMNS)
|
11
|
+
self.gsub(/\n/, ' ').gsub(/.{1,#{columns}}(?:\s|\Z)/){$&+"\n"}
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
data/lib/rex/numeric.rb
ADDED
@@ -0,0 +1,19 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# numeric.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
require 'modules/ordinal'
|
7
|
+
require 'modules/roman'
|
8
|
+
|
9
|
+
class Numeric
|
10
|
+
# Integer#to_ordinal
|
11
|
+
# Integer#from_ordinal(ordinal)
|
12
|
+
include Ordinal
|
13
|
+
|
14
|
+
# Integer#to_roman
|
15
|
+
# Integer#from_roman(roman)
|
16
|
+
include Roman
|
17
|
+
end
|
18
|
+
|
19
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
data/lib/rex/string.rb
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# string.rb
|
4
|
+
# yesmar@speakeasy.net
|
5
|
+
|
6
|
+
require 'modules/propercase'
|
7
|
+
require 'modules/scrub'
|
8
|
+
require 'modules/wrap'
|
9
|
+
|
10
|
+
class String
|
11
|
+
# String#propercase
|
12
|
+
include ProperCase
|
13
|
+
|
14
|
+
# String#scrub
|
15
|
+
include Scrub
|
16
|
+
|
17
|
+
# String#wrap(cols=78)
|
18
|
+
include Wrap
|
19
|
+
end
|
20
|
+
|
21
|
+
raise RuntimeError, 'This library is for require only' if $0 == __FILE__
|
data/lib/rex/symbol.rb
ADDED