simple_transitions 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.gitignore +4 -0
- data/Gemfile +4 -0
- data/README.rdoc +4 -0
- data/Rakefile +8 -0
- data/lib/simple_transitions.rb +9 -0
- data/lib/simple_transitions/definition.rb +29 -0
- data/lib/simple_transitions/form_builder.rb +15 -0
- data/lib/simple_transitions/model.rb +30 -0
- data/lib/simple_transitions/version.rb +3 -0
- data/simple_state_machine.gemspec +28 -0
- data/spec/model_spec.rb +46 -0
- data/spec/spec_helper.rb +18 -0
- metadata +121 -0
data/.gitignore
ADDED
data/Gemfile
ADDED
data/README.rdoc
ADDED
data/Rakefile
ADDED
@@ -0,0 +1,9 @@
|
|
1
|
+
require 'active_record'
|
2
|
+
require 'action_view'
|
3
|
+
|
4
|
+
require 'simple_transitions/definition'
|
5
|
+
require 'simple_transitions/form_builder'
|
6
|
+
require 'simple_transitions/model'
|
7
|
+
|
8
|
+
ActiveRecord::Base.send :include, SimpleTransitions::Model
|
9
|
+
ActionView::Helpers::FormBuilder.send(:include, SimpleTransitions::FormBuilder)
|
@@ -0,0 +1,29 @@
|
|
1
|
+
module SimpleTransitions
|
2
|
+
|
3
|
+
class Definition
|
4
|
+
def initialize(model, column, &block)
|
5
|
+
@model = model
|
6
|
+
@column = column
|
7
|
+
instance_eval(&block)
|
8
|
+
end
|
9
|
+
|
10
|
+
def transition(transition_name, options)
|
11
|
+
from, to = options.values_at(:from, :to)
|
12
|
+
callback = options[:callback]
|
13
|
+
writer_method = "_#{transition_name}="
|
14
|
+
column = @column
|
15
|
+
|
16
|
+
[from].flatten.each do |from_state|
|
17
|
+
@model.available_transitions[from_state] << "_#{transition_name}"
|
18
|
+
end
|
19
|
+
|
20
|
+
# define a writer method so an appropriately named submit button can trigger the transition
|
21
|
+
@model.send(:define_method, writer_method) do |unused_value|
|
22
|
+
new_state = to.respond_to?(:call) ? to.call(self) : to
|
23
|
+
self.send("#{column}=", new_state)
|
24
|
+
self.current_transition = transition_name
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module SimpleTransitions
|
2
|
+
|
3
|
+
module FormBuilder
|
4
|
+
def transition_submit_buttons
|
5
|
+
submits = []
|
6
|
+
|
7
|
+
@object.available_transitions.each do |transition|
|
8
|
+
submits << submit("Save & #{transition.to_s.humanize.titleize.strip}", :name => "#{@object_name}[#{transition}]")
|
9
|
+
end
|
10
|
+
|
11
|
+
submits.join.html_safe
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
module SimpleTransitions
|
2
|
+
|
3
|
+
module Model
|
4
|
+
def self.included(base)
|
5
|
+
base.extend(ClassMethods)
|
6
|
+
end
|
7
|
+
|
8
|
+
def transitioning?(transition_name)
|
9
|
+
current_transition == transition_name
|
10
|
+
end
|
11
|
+
|
12
|
+
module ClassMethods
|
13
|
+
def simple_transitions(column, &block)
|
14
|
+
@available_transitions = Hash.new { |h,k| h[k] = [] }
|
15
|
+
class << self
|
16
|
+
attr_accessor :available_transitions
|
17
|
+
end
|
18
|
+
|
19
|
+
attr_accessor :current_transition
|
20
|
+
|
21
|
+
define_method :available_transitions do
|
22
|
+
self.class.available_transitions[self.send(column)]
|
23
|
+
end
|
24
|
+
|
25
|
+
SimpleTransitions::Definition.new(self, column, &block)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
$:.push File.expand_path("../lib", __FILE__)
|
3
|
+
require "simple_transitions/version"
|
4
|
+
|
5
|
+
Gem::Specification.new do |s|
|
6
|
+
s.name = "simple_transitions"
|
7
|
+
s.version = SimpleTransitions::VERSION
|
8
|
+
s.platform = Gem::Platform::RUBY
|
9
|
+
s.authors = ["Adam McCrea"]
|
10
|
+
s.email = ["adam@edgecase.com"]
|
11
|
+
s.homepage = ""
|
12
|
+
s.summary = %q{Minimalist state machine (not really) for Rails}
|
13
|
+
s.description = %q{
|
14
|
+
This gem doesn't really implement a state machine. All it really does is provide
|
15
|
+
an easy way to transition a model from one status to another using standard form
|
16
|
+
submit buttons, while also saving other changes made to that model.
|
17
|
+
}
|
18
|
+
|
19
|
+
s.files = `git ls-files`.split("\n")
|
20
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
21
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
22
|
+
s.require_paths = ["lib"]
|
23
|
+
|
24
|
+
s.add_dependency 'activerecord', '~> 3.0.3'
|
25
|
+
s.add_dependency 'actionpack', '~> 3.0.3'
|
26
|
+
|
27
|
+
s.add_development_dependency 'rspec', '~> 2.4.0'
|
28
|
+
end
|
data/spec/model_spec.rb
ADDED
@@ -0,0 +1,46 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe SimpleTransitions::Model do
|
4
|
+
|
5
|
+
let(:order) { Order.new }
|
6
|
+
|
7
|
+
describe "#available_transitions" do
|
8
|
+
it "always returns an array" do
|
9
|
+
order.status = 'invalid'
|
10
|
+
order.available_transitions.should == []
|
11
|
+
end
|
12
|
+
|
13
|
+
it "returns only the transitions that are available to the current state" do
|
14
|
+
order.status = 'paid'
|
15
|
+
order.available_transitions.should == ['_cancel']
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
describe "writer methods for transitioning state" do
|
20
|
+
it "are generated for each transition" do
|
21
|
+
order.should respond_to(:_pay=)
|
22
|
+
order.should respond_to(:_cancel=)
|
23
|
+
end
|
24
|
+
|
25
|
+
it "set the state column on the model to the appropriate next state" do
|
26
|
+
order.status = 'pending'
|
27
|
+
order._pay = 'whatever'
|
28
|
+
order.status.should == 'paid'
|
29
|
+
end
|
30
|
+
|
31
|
+
it "set the state column on the model from multiple statues to next state" do
|
32
|
+
['pending', 'paid'].each do |from|
|
33
|
+
order.status = from
|
34
|
+
order._cancel = 'whatever'
|
35
|
+
order.status.should == 'cancelled'
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
it "set the state using a proc" do
|
40
|
+
order.status = 'paid'
|
41
|
+
order.should_receive(:next_status)
|
42
|
+
order._next = 'whatever'
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'bundler'
|
2
|
+
Bundler.require(:default, :development)
|
3
|
+
|
4
|
+
class Order
|
5
|
+
extend SimpleTransitions::Model::ClassMethods
|
6
|
+
attr_accessor :status
|
7
|
+
|
8
|
+
simple_transitions :status do
|
9
|
+
transition :pay, :from => 'pending', :to => 'paid'
|
10
|
+
transition :cancel, :from => ['pending', 'paid'], :to => 'cancelled'
|
11
|
+
transition :next, :from => 'incomplete', :to => proc { |o| o.next_status }
|
12
|
+
end
|
13
|
+
|
14
|
+
def next_status
|
15
|
+
'complete'
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
metadata
ADDED
@@ -0,0 +1,121 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: simple_transitions
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
prerelease: false
|
5
|
+
segments:
|
6
|
+
- 0
|
7
|
+
- 0
|
8
|
+
- 1
|
9
|
+
version: 0.0.1
|
10
|
+
platform: ruby
|
11
|
+
authors:
|
12
|
+
- Adam McCrea
|
13
|
+
autorequire:
|
14
|
+
bindir: bin
|
15
|
+
cert_chain: []
|
16
|
+
|
17
|
+
date: 2011-03-02 00:00:00 -05:00
|
18
|
+
default_executable:
|
19
|
+
dependencies:
|
20
|
+
- !ruby/object:Gem::Dependency
|
21
|
+
name: activerecord
|
22
|
+
prerelease: false
|
23
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
24
|
+
none: false
|
25
|
+
requirements:
|
26
|
+
- - ~>
|
27
|
+
- !ruby/object:Gem::Version
|
28
|
+
segments:
|
29
|
+
- 3
|
30
|
+
- 0
|
31
|
+
- 3
|
32
|
+
version: 3.0.3
|
33
|
+
type: :runtime
|
34
|
+
version_requirements: *id001
|
35
|
+
- !ruby/object:Gem::Dependency
|
36
|
+
name: actionpack
|
37
|
+
prerelease: false
|
38
|
+
requirement: &id002 !ruby/object:Gem::Requirement
|
39
|
+
none: false
|
40
|
+
requirements:
|
41
|
+
- - ~>
|
42
|
+
- !ruby/object:Gem::Version
|
43
|
+
segments:
|
44
|
+
- 3
|
45
|
+
- 0
|
46
|
+
- 3
|
47
|
+
version: 3.0.3
|
48
|
+
type: :runtime
|
49
|
+
version_requirements: *id002
|
50
|
+
- !ruby/object:Gem::Dependency
|
51
|
+
name: rspec
|
52
|
+
prerelease: false
|
53
|
+
requirement: &id003 !ruby/object:Gem::Requirement
|
54
|
+
none: false
|
55
|
+
requirements:
|
56
|
+
- - ~>
|
57
|
+
- !ruby/object:Gem::Version
|
58
|
+
segments:
|
59
|
+
- 2
|
60
|
+
- 4
|
61
|
+
- 0
|
62
|
+
version: 2.4.0
|
63
|
+
type: :development
|
64
|
+
version_requirements: *id003
|
65
|
+
description: "\n This gem doesn't really implement a state machine. All it really does is provide\n an easy way to transition a model from one status to another using standard form\n submit buttons, while also saving other changes made to that model.\n "
|
66
|
+
email:
|
67
|
+
- adam@edgecase.com
|
68
|
+
executables: []
|
69
|
+
|
70
|
+
extensions: []
|
71
|
+
|
72
|
+
extra_rdoc_files: []
|
73
|
+
|
74
|
+
files:
|
75
|
+
- .gitignore
|
76
|
+
- Gemfile
|
77
|
+
- README.rdoc
|
78
|
+
- Rakefile
|
79
|
+
- lib/simple_transitions.rb
|
80
|
+
- lib/simple_transitions/definition.rb
|
81
|
+
- lib/simple_transitions/form_builder.rb
|
82
|
+
- lib/simple_transitions/model.rb
|
83
|
+
- lib/simple_transitions/version.rb
|
84
|
+
- simple_state_machine.gemspec
|
85
|
+
- spec/model_spec.rb
|
86
|
+
- spec/spec_helper.rb
|
87
|
+
has_rdoc: true
|
88
|
+
homepage: ""
|
89
|
+
licenses: []
|
90
|
+
|
91
|
+
post_install_message:
|
92
|
+
rdoc_options: []
|
93
|
+
|
94
|
+
require_paths:
|
95
|
+
- lib
|
96
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
97
|
+
none: false
|
98
|
+
requirements:
|
99
|
+
- - ">="
|
100
|
+
- !ruby/object:Gem::Version
|
101
|
+
segments:
|
102
|
+
- 0
|
103
|
+
version: "0"
|
104
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
105
|
+
none: false
|
106
|
+
requirements:
|
107
|
+
- - ">="
|
108
|
+
- !ruby/object:Gem::Version
|
109
|
+
segments:
|
110
|
+
- 0
|
111
|
+
version: "0"
|
112
|
+
requirements: []
|
113
|
+
|
114
|
+
rubyforge_project:
|
115
|
+
rubygems_version: 1.3.7
|
116
|
+
signing_key:
|
117
|
+
specification_version: 3
|
118
|
+
summary: Minimalist state machine (not really) for Rails
|
119
|
+
test_files:
|
120
|
+
- spec/model_spec.rb
|
121
|
+
- spec/spec_helper.rb
|