bud 0.0.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (62) hide show
  1. data/LICENSE +9 -0
  2. data/README +30 -0
  3. data/bin/budplot +134 -0
  4. data/bin/budvis +201 -0
  5. data/bin/rebl +4 -0
  6. data/docs/README.md +13 -0
  7. data/docs/bfs.md +379 -0
  8. data/docs/bfs.raw +251 -0
  9. data/docs/bfs_arch.png +0 -0
  10. data/docs/bloom-loop.png +0 -0
  11. data/docs/bust.md +83 -0
  12. data/docs/cheat.md +291 -0
  13. data/docs/deploy.md +96 -0
  14. data/docs/diffs +181 -0
  15. data/docs/getstarted.md +296 -0
  16. data/docs/intro.md +36 -0
  17. data/docs/modules.md +112 -0
  18. data/docs/operational.md +96 -0
  19. data/docs/rebl.md +99 -0
  20. data/docs/ruby_hooks.md +19 -0
  21. data/docs/visualizations.md +75 -0
  22. data/examples/README +1 -0
  23. data/examples/basics/hello.rb +12 -0
  24. data/examples/basics/out +1103 -0
  25. data/examples/basics/out.new +856 -0
  26. data/examples/basics/paths.rb +51 -0
  27. data/examples/bust/README.md +9 -0
  28. data/examples/bust/bustclient-example.rb +23 -0
  29. data/examples/bust/bustinspector.html +135 -0
  30. data/examples/bust/bustserver-example.rb +18 -0
  31. data/examples/chat/README.md +9 -0
  32. data/examples/chat/chat.rb +45 -0
  33. data/examples/chat/chat_protocol.rb +8 -0
  34. data/examples/chat/chat_server.rb +29 -0
  35. data/examples/deploy/tokenring-ec2.rb +26 -0
  36. data/examples/deploy/tokenring-local.rb +17 -0
  37. data/examples/deploy/tokenring.rb +39 -0
  38. data/lib/bud/aggs.rb +126 -0
  39. data/lib/bud/bud_meta.rb +185 -0
  40. data/lib/bud/bust/bust.rb +126 -0
  41. data/lib/bud/bust/client/idempotence.rb +10 -0
  42. data/lib/bud/bust/client/restclient.rb +49 -0
  43. data/lib/bud/collections.rb +937 -0
  44. data/lib/bud/depanalysis.rb +44 -0
  45. data/lib/bud/deploy/countatomicdelivery.rb +50 -0
  46. data/lib/bud/deploy/deployer.rb +67 -0
  47. data/lib/bud/deploy/ec2deploy.rb +200 -0
  48. data/lib/bud/deploy/localdeploy.rb +41 -0
  49. data/lib/bud/errors.rb +15 -0
  50. data/lib/bud/graphs.rb +405 -0
  51. data/lib/bud/joins.rb +300 -0
  52. data/lib/bud/rebl.rb +314 -0
  53. data/lib/bud/rewrite.rb +523 -0
  54. data/lib/bud/rtrace.rb +27 -0
  55. data/lib/bud/server.rb +43 -0
  56. data/lib/bud/state.rb +108 -0
  57. data/lib/bud/storage/tokyocabinet.rb +170 -0
  58. data/lib/bud/storage/zookeeper.rb +178 -0
  59. data/lib/bud/stratify.rb +83 -0
  60. data/lib/bud/viz.rb +65 -0
  61. data/lib/bud.rb +797 -0
  62. metadata +330 -0
data/LICENSE ADDED
@@ -0,0 +1,9 @@
1
+ Copyright (c) 2011, Regents of the University of California
2
+ All rights reserved.
3
+
4
+ Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
5
+
6
+ o Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
7
+ o Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
8
+ o Neither the name of the University of California, Berkeley nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
9
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
data/README ADDED
@@ -0,0 +1,30 @@
1
+ # Bud
2
+
3
+ This is Bud, a.k.a. "Bloom Under Development". It is an initial cut at a Bloom DSL, using Ruby as a setting.
4
+
5
+ Please see LICENSE for licensing information.
6
+
7
+ Language cheatsheet in doc/cheat.md
8
+
9
+ Main deficiencies at this point are:
10
+ - Inefficient evaluation: Programs are run using semi-naive evaluation strategies, but no further
11
+ query optimization has been implemented, and little effort has been spent in
12
+ tuning.
13
+
14
+ - No Ruby constraints: Within Bloom programs the full power of Ruby is also available, including mutable state.
15
+ This allows programmers to get outside the Bloom framework and lose cleanliness.
16
+
17
+ - Compatibility: Bud only works with Ruby (MRI) 1.8. MRI 1.9, JRuby and other Ruby
18
+ implementations are currently not supported.
19
+
20
+ To install:
21
+ % gem install bud
22
+
23
+ Simple example programs can be found in examples. A much larger set
24
+ of example programs and libraries can be found in the bud-sandbox repo.
25
+
26
+ ## Optional Dependencies
27
+
28
+ The bud gem has a handful of mandatory dependencies. It also has one optional
29
+ dependency: if you wish to use the Bud collections backed by Zookeeper (the
30
+ "zktable" collection type), the "zookeeper" gem must be installed.
data/bin/budplot ADDED
@@ -0,0 +1,134 @@
1
+ #!/usr/bin/env ruby
2
+ require 'rubygems'
3
+ require 'bud'
4
+ require 'bud/bud_meta'
5
+ require 'bud/graphs'
6
+ require 'bud/depanalysis'
7
+
8
+ # args: N, files_n, classes_m
9
+
10
+ def process(mods)
11
+ classdef = "class FooBar\ninclude Bud\n" + mods.map{|m| "include #{m}"}.join("\n") + "\nend\n FooBar.new"
12
+ puts "classdef #{classdef}"
13
+ d = eval(classdef)
14
+
15
+ d.t_rules.each {|s| puts "RULE: #{s.inspect}" }
16
+ #d.t_depends.each {|s| puts "DEP: #{s.inspect}" }
17
+
18
+ da = d.meta_parser.depanalysis
19
+
20
+ #puts "MP info src=#{da.source.length}, snk=#{da.sink.length}, under=#{da.underspecified.length}"
21
+
22
+ #d.meta_parser.depanalysis.source.each do |s|
23
+ # puts "SRC: #{s}"
24
+ #end
25
+
26
+ interfaces = {}
27
+ d.t_provides.each do |name, is_input|
28
+ interfaces[name] = is_input
29
+ end
30
+
31
+ tabinf = {}
32
+ inp = []
33
+ outp = []
34
+ priv = []
35
+ d.tables.each do |t|
36
+ tab = t[0].to_s
37
+ tabinf[tab] = t[1].class.to_s
38
+ if interfaces[tab].nil?
39
+ unless tab =~ /^t_/ or tab == "stdio" or tab == "localtick"
40
+ priv << t
41
+ end
42
+ else
43
+ if interfaces[tab]
44
+ inp << t
45
+ else
46
+ outp << t
47
+ end
48
+ end
49
+ end
50
+
51
+ svg = "bud_doc/" + mods.join("_") + "_viz"
52
+ write_index(inp, outp, priv, svg)
53
+ gv = GraphGen.new(d.t_stratum, tabinf, d.t_cycle, svg, -1, 1, ".", true, d.meta_parser.depanalysis)
54
+ gv.process(d.t_depends)
55
+ gv.dump(d.t_rules)
56
+ gv.finish
57
+
58
+ gv2 = GraphGen.new(d.t_stratum, tabinf, d.t_cycle, svg, -1, 1, ".", false, d.meta_parser.depanalysis)
59
+ gv2.process(d.t_depends)
60
+ gv2.dump(d.t_rules)
61
+ gv2.finish
62
+ end
63
+
64
+ def write_index(inp, outp, priv, svg)
65
+ f = File.open("bud_doc/index.html", "w")
66
+ f.puts "<html>"
67
+ f.puts "<embed src=\"#{ENV['PWD']}/#{svg}_collapsed.svg\" width=\"100%\" height=\"60%\" type=\"image/svg+xml\" pluginspage=\"http://www.adobe.com/svg/viewer/install/\" />"
68
+
69
+ f.puts "<table border='1' valign='top' width = '100%'><tr valign='top'>"
70
+ f.puts "<td valign='top'>"
71
+ f.puts "<h2> Input Interfaces </h2>"
72
+ do_table(f, inp)
73
+ f.puts "</td><td>"
74
+ f.puts "<h2> Output Interfaces </h2>"
75
+ do_table(f, outp)
76
+ f.puts "</td><td>"
77
+ f.puts "<h2> Private State </h2>"
78
+ do_table(f, priv, true)
79
+ f.puts "</td>"
80
+ f.puts "</tr></table>"
81
+ f.puts "</html>"
82
+ f.close
83
+ end
84
+
85
+ def do_table(f, info, type=false)
86
+ next if info.nil?
87
+ f.puts "<table border='1'>"
88
+ info.sort{|a, b| a[0].to_s <=> b[0].to_s}.each do |inf|
89
+ #f.puts "<h3>#{inf[0]}</h3>"
90
+ #f.puts "&nbsp; (#{inf[1].class.to_s.gsub('Bud::Bud', '')})<br>" if type
91
+ unless inf[1].schema.nil?
92
+ f.puts "<tr><td><b>#{inf[0]}</b></td>" + inf[1].schema.map{|i| "<td>#{i}</td>"}.join(" ") + "</tr>"
93
+ end
94
+ end
95
+ f.puts "</table>"
96
+ end
97
+
98
+ @shreddies = []
99
+ @provides = []
100
+ @demands = []
101
+ @tabinf = {}
102
+ @port = 12345
103
+ files = []
104
+ classes = []
105
+
106
+ if ARGV.length < 2
107
+ puts "len #{ARGV.length} USAGE:\nruby plotter.rb LIST_OF_FILES LIST_OF_MODULES"
108
+ exit
109
+ end
110
+
111
+ `mkdir bud_doc`
112
+
113
+ modules = []
114
+ (0..ARGV.length-1).each do |i|
115
+ begin
116
+ f = File.open(ARGV[i])
117
+ mods = false
118
+ rescue
119
+ mods = true
120
+ end
121
+
122
+ unless mods
123
+ puts "DO #{ARGV[i]}"
124
+ eval ( "require \"#{ARGV[i]}\"")
125
+ else
126
+ puts "Work on #{ARGV[i]}"
127
+ #instant(ARGV[i])
128
+ modules << ARGV[i]
129
+ puts "OK"
130
+ end
131
+ end
132
+
133
+ process(modules)
134
+
data/bin/budvis ADDED
@@ -0,0 +1,201 @@
1
+ #!/usr/bin/env ruby
2
+ require 'rubygems'
3
+ require 'tokyocabinet'
4
+ require 'bud'
5
+ require 'bud/graphs'
6
+ include TokyoCabinet
7
+
8
+ # prototype offline viz
9
+
10
+ BUD_TC_DIR = "#{ARGV[0]}/bud_"
11
+
12
+
13
+ class VizHelper
14
+ include Bud
15
+
16
+ state do
17
+ table :full_info, [:bud_time, :table, :row]
18
+ scratch :cardinalities, [:bud_time, :table] => [:cnt]
19
+ scratch :times, [:bud_time]
20
+ end
21
+
22
+ def initialize(strata, tabinf, cycle, depends, rules, dir)
23
+ @t_strata = strata
24
+ @t_tabinf = tabinf
25
+ @t_cycle = cycle
26
+ @t_depends = depends
27
+ @dir = dir
28
+ @t_rules = rules
29
+ super()
30
+ end
31
+
32
+ bloom :counting do
33
+ cardinalities <= full_info.group([full_info.bud_time, full_info.table], count)
34
+ times <= full_info.map{|f| [f.bud_time]}
35
+ end
36
+
37
+ def summarize(dir, schema)
38
+ table_io = {}
39
+ timeseries = {}
40
+ cardinalities.sort{|a, b| a[0] <=> b[0]}.each do |card|
41
+ table_io["#{card.table}_#{card.bud_time}"] = start_table(dir, card.table, card.bud_time, schema[card.table])
42
+ unless timeseries[card.table]
43
+ timeseries[card.table] = []
44
+ end
45
+ timeseries[card.table] << card.cnt
46
+ end
47
+ full_info.each do |info|
48
+ write_table_content(table_io["#{info.table}_#{info.bud_time}"], info.row)
49
+ end
50
+
51
+ table_io.each_value do |tab|
52
+ end_table(tab)
53
+ end
54
+
55
+ ts2 = {}
56
+ timeseries.each_pair do |k, v|
57
+ fn = v
58
+ puts "GOT #{fn}"
59
+ #ts2[k] = "#{ENV['PWD']}/#{fn}"
60
+ ts2[k] = v
61
+ end
62
+
63
+ sum = GraphGen.new(@t_strata, @t_tabinf, @t_cycle, "#{@dir}/summary", -1, 3, @dir, false, nil, ts2)
64
+ sum.process(@t_depends)
65
+ sum.dump(@t_rules)
66
+ sum.finish
67
+
68
+ # fix: nested loops
69
+ times.sort.each do |time|
70
+ card_info = {}
71
+ cardinalities.each do |card|
72
+ if card.bud_time == time.bud_time
73
+ card_info[card.table] = card.cnt
74
+ end
75
+ end
76
+
77
+ gv = GraphGen.new(@t_strata, @t_tabinf, @t_cycle, "#{@dir}/tm_#{time.bud_time}", time.bud_time, 3, @dir, false, nil, card_info)
78
+ gv.process(@t_depends)
79
+ gv.dump(@t_rules)
80
+ gv.finish
81
+
82
+ end
83
+
84
+ end
85
+
86
+ def start_table(dir, tab, time, schema)
87
+ str = "#{dir}/#{tab}_#{time}.html"
88
+ #fout = File.new("#{dir}/#{tab}_#{time}.html", "w")
89
+ fout = File.new(str, "w")
90
+
91
+ #fout.puts "<h1>#{tab} #{time_node_header()}</h1>"
92
+ fout.puts "<html><title>#{tab} @ #{time}</title>"
93
+ fout.puts "<table border=1>"
94
+ fout.puts "<tr>" + schema.map{|s| "<th> #{s} </th>"}.join(" ") + "<tr>"
95
+ fout.close
96
+ return str
97
+ end
98
+
99
+ def end_table(stream)
100
+ fp = File.open(stream, "a")
101
+ fp.puts "</table>"
102
+ fp.close
103
+ end
104
+
105
+ def write_table_content(fn, row)
106
+ stream = File.open(fn, "a")
107
+ stream.puts "<tr>"
108
+ stream.puts row.map{|c| "<td>#{c.to_s}</td>"}.join(" ")
109
+ stream.puts "</tr>"
110
+ stream.close
111
+ end
112
+ end
113
+
114
+ def deserialize_table(tab, strict)
115
+ # oy. meta only
116
+ ret = []
117
+ tab.each_pair do |k, v|
118
+ #key = Marshal.load(k)
119
+ key = MessagePack.unpack(k)
120
+ time = key.shift
121
+ raise "non-zero budtime. sure this is metadata?" if time != 0 and strict
122
+ tup = key
123
+ #Marshal.load(v).each{|v| tup << v }
124
+ MessagePack.unpack(v).each{|val| tup << val }
125
+ ret << tup
126
+ end
127
+ tab.close
128
+ return ret
129
+ end
130
+
131
+ def usage
132
+ puts "Usage:"
133
+ puts "Running a Bud program with option :visualize => 3 will cause a TC directory TC_dir to be created (Class_ObjectId_Port)"
134
+ puts "> ruby visualize.rb TC_dir"
135
+ puts "This will create a series of svg files in TC_dir, the root of which will be named tm_0_expanded.svg. Open in a browser.\n"
136
+ puts "e.g."
137
+ puts "> ruby test/tc_carts.rb"
138
+ puts "> ruby visualize.rb BCS_2159661360_"
139
+ puts "> open -a /Applications/Google\ Chrome.app/ BCS_2159661360_/tm_0_expanded.svg"
140
+ exit
141
+ end
142
+
143
+ # begin "main"
144
+
145
+ usage unless ARGV[0]
146
+
147
+ @tables = {}
148
+
149
+ Dir.new(BUD_TC_DIR).entries.each do |file|
150
+ next if file =~ /^\./
151
+ puts "FILE is #{file}"
152
+ hdb = TokyoCabinet::HDB.new
153
+ ret = hdb.open("#{BUD_TC_DIR}/#{file}", HDB::OREADER)
154
+ raise "db not found" unless ret
155
+ @tables[file] = hdb
156
+ end
157
+
158
+
159
+ # let's try to do a visualization
160
+ strata = deserialize_table(@tables['t_stratum_vizlog.tch'], true)
161
+ tabinf = deserialize_table(@tables['t_table_info_vizlog.tch'], true)
162
+ tabscm = deserialize_table(@tables['t_table_schema_vizlog.tch'], true)
163
+ cycle = deserialize_table(@tables['t_cycle_vizlog.tch'], true)
164
+ depends = deserialize_table(@tables['t_depends_vizlog.tch'], true)
165
+ rules = deserialize_table(@tables['t_rules_vizlog.tch'], true)
166
+
167
+
168
+ schminf = {}
169
+ tabscm.each do |ts|
170
+ puts "TABSCM: #{ts.inspect}"
171
+ tab = ts[0].to_s
172
+ unless schminf[tab]
173
+ schminf[tab] = []
174
+ end
175
+ schminf[tab][ts[2]] = ts[1]
176
+ end
177
+
178
+ gv = GraphGen.new(strata, tabinf, cycle, "OUTPUT", -1, 1, "plotter_out")
179
+ gv.process(depends)
180
+ gv.finish
181
+
182
+
183
+ vh = VizHelper.new(strata, tabinf, cycle, depends, rules, ARGV[0])
184
+
185
+ @tables.each_pair do |name, contents|
186
+ name = name.gsub("_vizlog.tch", "")
187
+ contents.each_pair do |k, v|
188
+ key = MessagePack.unpack(k)
189
+ time = key[0]
190
+ row = key
191
+ MessagePack.unpack(v).each{ |val| row << val }
192
+ if name == "t_table_info.tch" or name == "t_table_schema.tch"
193
+ #vh.full_info << [0, name, row]
194
+ else
195
+ vh.full_info << [time, name, row]
196
+ end
197
+ end
198
+ end
199
+
200
+ vh.tick
201
+ vh.summarize(ARGV[0], schminf)
data/bin/rebl ADDED
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env ruby
2
+ require 'bud/rebl'
3
+
4
+ ReblShell::run
data/docs/README.md ADDED
@@ -0,0 +1,13 @@
1
+ #Bud: Bloom under development#
2
+ Welcome to the documentation for *Bud*, a prototype of Bloom under development.
3
+
4
+ The documents here are organized to be read in any order, but you might like to try the following:
5
+
6
+ * [intro.md](intro.md): A brief introduction to Bud and Bloom
7
+ * [getstarted.md](getstarted.md): A quickstart to teach you basic Bloom concepts, the use of `rebl` interactive terminal, and the embedding of Bloom code in Ruby via the `Bud` module.
8
+ * [operational.md](operational.md): an operational view of Bloom, to provide a more detailed model of how Bloom code is evaluated by Bud.
9
+ * [Bud RubyDoc](http://rubydoc.info/github/bloom-lang/bud/): RubyDoc on the language constructs and runtime hooks provided by the Bud module
10
+ * [cheat.md](cheat.md): A concise "cheat sheet" to remind you about Bloom syntax.
11
+ * [ruby_hooks.md](ruby_hooks.md): Bud module methods that allow you to interact with the Bud evaluator from other Ruby threads.
12
+ * [bud-sandbox](http://github.com/bloom-lang/bud-sandbox): a github repository including lots of useful libraries and examples.
13
+ * [bfs.md](bfs.md): A walkthrough of the Bloom distributed filesystem.