Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
tag: v4.0.0.beta1
Fetching contributors…

Cannot retrieve contributors at this time

157 lines (128 sloc) 4.068 kb
require 'action_dispatch/journey/nfa/dot'
module ActionDispatch
module Journey # :nodoc:
module GTG # :nodoc:
class TransitionTable # :nodoc:
include Journey::NFA::Dot
attr_reader :memos
def initialize
@regexp_states = Hash.new { |h,k| h[k] = {} }
@string_states = Hash.new { |h,k| h[k] = {} }
@accepting = {}
@memos = Hash.new { |h,k| h[k] = [] }
end
def add_accepting(state)
@accepting[state] = true
end
def accepting_states
@accepting.keys
end
def accepting?(state)
@accepting[state]
end
def add_memo(idx, memo)
@memos[idx] << memo
end
def memo(idx)
@memos[idx]
end
def eclosure(t)
Array(t)
end
def move(t, a)
move_string(t, a).concat(move_regexp(t, a))
end
def to_json
require 'json'
simple_regexp = Hash.new { |h,k| h[k] = {} }
@regexp_states.each do |from, hash|
hash.each do |re, to|
simple_regexp[from][re.source] = to
end
end
JSON.dump({
regexp_states: simple_regexp,
string_states: @string_states,
accepting: @accepting
})
end
def to_svg
svg = IO.popen('dot -Tsvg', 'w+') { |f|
f.write(to_dot)
f.close_write
f.readlines
}
3.times { svg.shift }
svg.join.sub(/width="[^"]*"/, '').sub(/height="[^"]*"/, '')
end
def visualizer(paths, title = 'FSM')
viz_dir = File.join File.dirname(__FILE__), '..', 'visualizer'
fsm_js = File.read File.join(viz_dir, 'fsm.js')
fsm_css = File.read File.join(viz_dir, 'fsm.css')
erb = File.read File.join(viz_dir, 'index.html.erb')
states = "function tt() { return #{to_json}; }"
fun_routes = paths.shuffle.first(3).map do |ast|
ast.map { |n|
case n
when Nodes::Symbol
case n.left
when ':id' then rand(100).to_s
when ':format' then %w{ xml json }.shuffle.first
else
'omg'
end
when Nodes::Terminal then n.symbol
else
nil
end
}.compact.join
end
stylesheets = [fsm_css]
svg = to_svg
javascripts = [states, fsm_js]
# Annoying hack for 1.9 warnings
fun_routes = fun_routes
stylesheets = stylesheets
svg = svg
javascripts = javascripts
require 'erb'
template = ERB.new erb
template.result(binding)
end
def []=(from, to, sym)
case sym
when String
@string_states[from][sym] = to
when Regexp
@regexp_states[from][sym] = to
else
raise ArgumentError, 'unknown symbol: %s' % sym.class
end
end
def states
ss = @string_states.keys + @string_states.values.map(&:values).flatten
rs = @regexp_states.keys + @regexp_states.values.map(&:values).flatten
(ss + rs).uniq
end
def transitions
@string_states.map { |from, hash|
hash.map { |s, to| [from, s, to] }
}.flatten(1) + @regexp_states.map { |from, hash|
hash.map { |s, to| [from, s, to] }
}.flatten(1)
end
private
def move_regexp(t, a)
return [] if t.empty?
t.map { |s|
@regexp_states[s].map { |re, v| re === a ? v : nil }
}.flatten.compact.uniq
end
def move_string(t, a)
return [] if t.empty?
t.map { |s| @string_states[s][a] }.compact
end
end
end
end
end
Jump to Line
Something went wrong with that request. Please try again.