#!/usr/bin/env ruby require 'trollop' require 'pp' opts = Trollop::options do version "#{$0} (c) 2008 Nate Murray" banner <<-EOS http://gist.github.com/16729 A tiny utility to generate graphviz dot files from objects that use pluginaweek's excellent state_machine library. (http://github.com/pluginaweek/state_machine/tree/master) Usage: #{$0} [opts] rails_root class" Examples: #{$0} /path/to/rails_root Order #{$0} . Order | dot -Tsvg -Grankdir=LR > graph.svg; open graph.svg Options: EOS opt :machine, "Which machine to read from a the class", :type => String, :default => "state" opt :name, "The name of the graph", :type => String, :default => "state" opt :font_name, "The name of the font to use", :type => String, :default => "Gill Sans" end unless ARGV.size >= 2 puts "Usage: #{$0} [opts] rails_root class" puts "Try: #{$0} --help to see all options" exit end rails_root, klass = ARGV[0], ARGV[1] require rails_root + "/config/environment.rb" puts "digraph #{opts[:name]} {" machine = klass.constantize.state_machines[opts[:machine]] machine.states.each do |state| shape = state == machine.instance_variable_get("@initial_state") ? "doublecircle" : "circle" puts %Q{#{state} [width=1,height=1,fixedsize=true,shape=#{shape},fontname="#{opts[:font_name]}"];} end puts machine.events.each do |event_name,event| event.transitions.each do |transition| if transition.options.has_key?(:to) && transition.options.has_key?(:from) froms = transition.options[:from].kind_of?(Array) ? transition.options[:from] : [ transition.options[:from] ] froms.each do |from| puts %Q{#{from} -> #{transition.options[:to]} [label="#{event_name}",fontname="#{opts[:font_name]}"];} end end end end puts "}"