midwire-wizard_controller 0.1.8

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,3 @@
1
+ *.gem
2
+ doc/
3
+ .specification
@@ -0,0 +1,3 @@
1
+ 20100129: 0.1.8 Midwire added the direct_step action, and supporting 'direct_step_path' method, to allow handling of navigating to a step directly instead of always using next and previous.
2
+ 20091102: 0.1.5 Changed session variable that stores redirect information, to avoid conflicts.
3
+ 20090925: Packaged as Gem
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2010 Midwire Technologies, LLC (midwire@midwire.com)
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
@@ -0,0 +1,84 @@
1
+ = Wizard Controller
2
+
3
+ Wizard controller provides a base class (Inheriting from ActionController::Base)
4
+ that provides a DSL for quickly making Wizards.
5
+
6
+ VERY IMPORTANT!!! DONT OVERRIDE INDEX!
7
+ Doing so will break all functionality. WizardController works by defining an
8
+ "index" method that does all the work. To start a wizard, go to the "index" method.
9
+
10
+ === Setup and Configuration
11
+
12
+ Add the following gem configuration to <tt>config/environment.rb</tt>
13
+
14
+ config.gem "wizard_controller"
15
+
16
+ Ensure the following is present in <tt>config/routes.rb</tt>
17
+
18
+ map.connect ':controller/:action/:id'
19
+
20
+ ... or explicitly map the routes you want to use.
21
+
22
+ === Example Controller
23
+
24
+ class ExampleController < Codeprimate::Wizard::Base
25
+ # Define the method names of the wixard steps
26
+ define_steps :page_one, :page_two, :page_three
27
+
28
+ # Specify where the Wizard should redirect upon completion.
29
+ set_finish_path "http://www.example.com/go_here_when_done.html"
30
+
31
+
32
+ # Ensure "index" is not defined!
33
+ # def index
34
+ # end
35
+
36
+ def start
37
+ # Create a "safe" index method for this controller, and handle it appropriately
38
+ end
39
+
40
+ def foobar
41
+ # You can define whatever actions you want. WizardController doesnt get in the way.
42
+ end
43
+
44
+ def page_one
45
+ # This is a regular action method. Create indiviual views for action methods.
46
+ end
47
+
48
+ def process_page_one
49
+ # Place logic to handle any output from page one here.
50
+ # No view will be shown for this
51
+ #
52
+ # Return true if your logic wants you to go to the next step
53
+ # Return false if you want to return to the page_one view
54
+ return true
55
+ end
56
+
57
+ def page_two
58
+ # Let's say this action/view is merely informative.
59
+ # We will not supply a process method, and the user will always be able
60
+ # to go to the next step
61
+ end
62
+
63
+ def page_three
64
+ # Just another step method here
65
+ end
66
+
67
+ def process_page_three
68
+ # Since this is the last step, if this process method returns true
69
+ # the user will be redirected to the URL specified in the
70
+ # "set_finish_path" declaration at the beginning of the Controller definition
71
+ end
72
+ end
73
+
74
+ === View Helper Methods
75
+
76
+ * <tt>step_number()</tt>: Current step index.
77
+ * <tt>total_steps()</tt>: Total Number of steps in the wizard.
78
+ * <tt>step_completed()</tt>: Returns boolean, whether the step has been completed.
79
+ * <tt>wizard_path()</tt>: Wizard index path. <b>THIS SHOULD BE THE ACTION PATH OF ALL FORMS/VIEWS WITH A "process" action.</b>
80
+ * <tt>next_step_path()</tt>: URL to the next step.
81
+ * <tt>previous_step_path()</tt>: URL to the previous step.
82
+ * <tt>direct_step_path()</tt>: URL to a direct step. Example for step 3: <code>direct_step_path(:id=>3)</code>. User will stay on the current step if they have not completed the one they are requesting.
83
+ * <tt>reset_wizard_path()</tt>: URL to reset the Wizard.
84
+ * <tt>abort_wizard_path()</tt>: URL to abort the Wizard.
@@ -0,0 +1,14 @@
1
+ begin
2
+ require 'jeweler'
3
+ Jeweler::Tasks.new do |gemspec|
4
+ gemspec.name = %q{midwire-wizard_controller}
5
+ gemspec.summary = %q{A simple way to create non-model-based Wizards}
6
+ gemspec.description = %q{Wizard controller provides a base class (Inheriting from ActionController::Base) that provides a DSL for quickly making Wizards.}
7
+ gemspec.email = "midwire@midwiretech.com"
8
+ gemspec.homepage = "http://github.com/midwire/wizard_controller"
9
+ gemspec.authors = ["Josh Nichols", "Midwire"]
10
+ end
11
+ Jeweler::GemcutterTasks.new
12
+ rescue LoadError
13
+ puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
14
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.1.8
@@ -0,0 +1,346 @@
1
+ module Codeprimate
2
+ # = Wizard Controller
3
+ #
4
+ # Wizard controller provides a base class (Inheriting from ActionController::Base)
5
+ # that provides a DSL for quickly making Wizards.
6
+ #
7
+ # VERY IMPORTANT!!! DONT OVERRIDE INDEX!
8
+ # Doing so will break all functionality. WizardController works by defining an
9
+ # "index" method that does all the work. To start a wizard, go to the "index" method.
10
+ #
11
+ # === Setup and Configuration
12
+ #
13
+ # Add the following gem configuration to <tt>config/environment.rb</tt>
14
+ #
15
+ # config.gem "wizard_controller"
16
+ #
17
+ # Ensure the following is present in <tt>config/routes.rb</tt>
18
+ #
19
+ # map.connect ':controller/:action/:id'
20
+ #
21
+ # === Example Controller
22
+ #
23
+ # class ExampleController < Codeprimate::Wizard::Base
24
+ # # Define the method names of the wixard steps
25
+ # define_steps :page_one, :page_two, :page_three
26
+ #
27
+ # # Specify where the Wizard should redirect upon completion.
28
+ # set_finish_path "http://www.example.com/go_here_when_done.html"
29
+ #
30
+ #
31
+ # # Ensure "index" is not defined!
32
+ # # def index
33
+ # # end
34
+ #
35
+ # def start
36
+ # # Create a "safe" index method for this controller, and handle it appropriately
37
+ # end
38
+ #
39
+ # def foobar
40
+ # # You can define whatever actions you want. WizardController doesnt get in the way.
41
+ # end
42
+ #
43
+ # def page_one
44
+ # # This is a regular action method. Create indiviual views for action methods.
45
+ # end
46
+ #
47
+ # def process_page_one
48
+ # # Place logic to handle any output from page one here.
49
+ # # No view will be shown for this
50
+ # #
51
+ # # Return true if your logic wants you to go to the next step
52
+ # # Return false if you want to return to the page_one view
53
+ # return true
54
+ # end
55
+ #
56
+ # def page_two
57
+ # # Let's say this action/view is merely informative.
58
+ # # We will not supply a process method, and the user will always be able
59
+ # # to go to the next step
60
+ # end
61
+ #
62
+ # def page_three
63
+ # # Just another step method here
64
+ # end
65
+ #
66
+ # def process_page_three
67
+ # # Since this is the last step, if this process method returns true
68
+ # # the user will be redirected to the URL specified in the
69
+ # # "set_finish_path" declaration at the beginning of the Controller definition
70
+ # end
71
+ # end
72
+ #
73
+ # === View Helper Methods
74
+ #
75
+ # * <tt>step_number()</tt>: Current step index.
76
+ # * <tt>total_steps()</tt>: Total Number of steps in the wizard.
77
+ # * <tt>step_completed()</tt>: Returns boolean, whether the step has been completed.
78
+ # * <tt>wizard_path()</tt>: Wizard index path. <b>THIS SHOULD BE THE ACTION PATH OF ALL FORMS/VIEWS WITH A "process" action.</b>
79
+ # * <tt>next_step_path()</tt>: URL to the next step.
80
+ # * <tt>previous_step_path()</tt>: URL to the previous step.
81
+ # * <tt>reset_wizard_path()</tt>: URL to reset the Wizard.
82
+ # * <tt>abort_wizard_path()</tt>: URL to abort the Wizard.
83
+ module Wizard
84
+ VERSION = "0.1.7"
85
+
86
+ class Base < ApplicationController
87
+ before_filter :restrict_access, :init_wizard_session
88
+
89
+ ### CLASS METHODS
90
+ class << self
91
+ @wizard_steps = []
92
+ @finish_path = '/'
93
+ @wizard_default_error = 'There was a problem processing the last step.'
94
+ attr_accessor :wizard_steps, :finish_path, :abort_path, :wizard_default_error
95
+
96
+ # Define steps of the wizard.
97
+ #
98
+ # Should be an array of symbols.
99
+ def define_steps(*args)
100
+ self.wizard_steps = args
101
+ end
102
+
103
+ # Set the URL that a user is redirected to after finishing the Wizard.
104
+ #
105
+ # Should be a string
106
+ def set_finish_path(p)
107
+ self.finish_path = p
108
+ end
109
+
110
+ # Set the URL that a user is redirected to after aborting the Wizard.
111
+ #
112
+ # Should be a string
113
+ def set_abort_path(p)
114
+ self.abort_path = p
115
+ end
116
+
117
+ # Set the flash message a user sees when a process_action method returns false
118
+ #
119
+ # Should be a string
120
+ def set_default_error(e)
121
+ self.wizard_default_error = e
122
+ end
123
+ end
124
+
125
+ ### PUBLIC ACTIONS
126
+
127
+ # Internal.
128
+ def index
129
+ if finished
130
+ handle_finished_wizard
131
+ else
132
+ handle_unfinished_wizard
133
+ end
134
+ end
135
+
136
+ # Internal.
137
+ def next_step
138
+ if step_completed
139
+ incr_step
140
+ else
141
+ flash[:error] ||= self.class.wizard_default_error
142
+ end
143
+ self.finish_path = params[:redirect] unless params[:redirect].blank?
144
+ redirect_to :action => :index
145
+ end
146
+
147
+ # Internal.
148
+ def previous_step
149
+ decr_step
150
+ redirect_to :action => :index
151
+ end
152
+
153
+ # Internal.
154
+ def direct_step
155
+ step = params[:id].to_i
156
+ if step_completed(step)
157
+ set_current_wizard_step([1, step].max)
158
+ else
159
+ flash[:error] ||= self.class.wizard_default_error
160
+ end
161
+ redirect_to :action => :index
162
+ end
163
+
164
+ # Public action to reset the wizard
165
+ def reset
166
+ reset_wizard
167
+ redirect_to :action => :index
168
+ end
169
+
170
+ # Assign finish path.
171
+ #
172
+ # Accepts a string.
173
+ def finish_path=(p)
174
+ unless p.blank?
175
+ session[:finish_path] = p
176
+ end
177
+ finish_path
178
+ end
179
+
180
+ private
181
+
182
+ ### PRIVATE CONTROLLER METHODS
183
+
184
+ def handle_finished_wizard
185
+ redirect_to finish_path
186
+ reset_wizard
187
+ end
188
+
189
+ def handle_unfinished_wizard
190
+ if request.get?
191
+ handle_get_action
192
+ else
193
+ handle_post_action
194
+ end
195
+ end
196
+
197
+ def handle_get_action
198
+ execute_method
199
+ render_step_view
200
+ end
201
+
202
+ def handle_post_action
203
+ if (self.wizard_step_completion = execute_process_method)
204
+ next_step
205
+ else
206
+ flash[:error] ||= self.class.wizard_default_error
207
+ render_step_view
208
+ end
209
+ end
210
+
211
+ def restrict_access
212
+ ['index', 'next_step', 'previous_step', 'direct_step', 'reset'].include?(params[:action])
213
+ end
214
+
215
+ def execute_method(m=current_wizard_step_method)
216
+ return send(m)
217
+ end
218
+
219
+ def execute_process_method
220
+ return execute_method("process_#{current_wizard_step_method}".to_sym)
221
+ end
222
+
223
+ def render_step_view
224
+ render :action => current_wizard_step_method
225
+ end
226
+
227
+ helper_method :step_number
228
+ def step_number
229
+ current_wizard_step
230
+ end
231
+
232
+ helper_method :total_steps
233
+ def total_steps
234
+ self.class.wizard_steps.size
235
+ end
236
+
237
+ helper_method :next_step_path
238
+ def next_step_path(options={})
239
+ url_for(({:controller => self.controller_name, :action => :next_step}).merge(options))
240
+ end
241
+
242
+ helper_method :previous_step_path
243
+ def previous_step_path
244
+ url_for(:controller => self.controller_name, :action => :previous_step)
245
+ end
246
+
247
+ helper_method :direct_step_path
248
+ def direct_step_path(step)
249
+ url_for(:controller => self.controller_name, :action => :direct_step, :id => step)
250
+ end
251
+
252
+ helper_method :step_completed
253
+ def step_completed(direct_step = current_wizard_step)
254
+ session[:wizard][self.class.to_s][:completed][direct_step] == true
255
+ end
256
+
257
+ helper_method :wizard_path
258
+ def wizard_path
259
+ url_for(:controller => self.controller_name)
260
+ end
261
+
262
+ helper_method :reset_wizard_path
263
+ def reset_wizard_path
264
+ url_for(:controller => self.controller_name, :action => :reset)
265
+ end
266
+
267
+
268
+ helper_method :abort_wizard_path
269
+ def abort_wizard_path
270
+ abort_path
271
+ end
272
+
273
+ #### SESSION MANAGEMENT
274
+
275
+ def current_wizard_step
276
+ @wizard_step ||= session[:wizard][self.class.to_s][:step].to_i
277
+ end
278
+
279
+ def set_current_wizard_step(step)
280
+ session[:wizard][self.class.to_s][:step] = step
281
+ @wizard_step = step
282
+ end
283
+
284
+ def incr_step
285
+ set_current_wizard_step(current_wizard_step + 1)
286
+ end
287
+
288
+ def decr_step
289
+ set_current_wizard_step([1, (current_wizard_step - 1)].max)
290
+ end
291
+
292
+ def current_wizard_step_method
293
+ self.class.wizard_steps[(current_wizard_step - 1)]
294
+ end
295
+
296
+ def finished
297
+ self.class.wizard_steps.size < current_wizard_step
298
+ end
299
+
300
+ def finish_path
301
+ # should be set to self.class.finish_path but that comes out to nil here somehow. --Dallas
302
+ fp = session[:finish_path] ||= self.class.finish_path ||= '/'
303
+ return fp
304
+ end
305
+
306
+ def abort_path=(p)
307
+ unless p.blank?
308
+ session[:abort_return_to] = p
309
+ end
310
+ abort_path
311
+ end
312
+
313
+ def abort_path
314
+ session[:abort_return_to] ||= self.class.abort_path ||= '/'
315
+ end
316
+
317
+ def no_processing
318
+ self.wizard_step_completion = true
319
+ end
320
+
321
+ def set_as_not_completed
322
+ self.wizard_step_completion = false
323
+ end
324
+
325
+ def wizard_step_completion=(completed)
326
+ session[:wizard][self.class.to_s][:completed][current_wizard_step] = completed
327
+ end
328
+
329
+ def reset_wizard
330
+ session[:wizard][self.class.to_s] = nil
331
+ init_wizard_session
332
+ end
333
+
334
+ def init_wizard_session
335
+ session[:wizard] ||= {}
336
+ session[:wizard][self.class.to_s] ||= {}
337
+ session[:wizard][self.class.to_s][:step] ||= 1
338
+ session[:wizard][self.class.to_s][:completed] ||= {}
339
+ session[:finish_path] ||= self.class.finish_path
340
+ @wizard_step = session[:wizard][self.class.to_s][:step].to_i
341
+ end
342
+
343
+ end
344
+ end
345
+
346
+ end
@@ -0,0 +1,45 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{midwire-wizard_controller}
8
+ s.version = "0.1.8"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["Josh Nichols", "Midwire"]
12
+ s.date = %q{2010-01-29}
13
+ s.description = %q{Wizard controller provides a base class (Inheriting from ActionController::Base) that provides a DSL for quickly making Wizards.}
14
+ s.email = %q{midwire@midwiretech.com}
15
+ s.extra_rdoc_files = [
16
+ "LICENSE",
17
+ "README.rdoc"
18
+ ]
19
+ s.files = [
20
+ ".gitignore",
21
+ "History.txt",
22
+ "LICENSE",
23
+ "README.rdoc",
24
+ "Rakefile",
25
+ "VERSION",
26
+ "lib/wizard_controller.rb",
27
+ "midwire-wizard_controller.gemspec"
28
+ ]
29
+ s.homepage = %q{http://github.com/midwire/wizard_controller}
30
+ s.rdoc_options = ["--charset=UTF-8"]
31
+ s.require_paths = ["lib"]
32
+ s.rubygems_version = %q{1.3.5}
33
+ s.summary = %q{A simple way to create non-model-based Wizards}
34
+
35
+ if s.respond_to? :specification_version then
36
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
37
+ s.specification_version = 3
38
+
39
+ if Gem::Version.new(Gem::RubyGemsVersion) >= Gem::Version.new('1.2.0') then
40
+ else
41
+ end
42
+ else
43
+ end
44
+ end
45
+
metadata ADDED
@@ -0,0 +1,64 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: midwire-wizard_controller
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.8
5
+ platform: ruby
6
+ authors:
7
+ - Josh Nichols
8
+ - Midwire
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2010-01-29 00:00:00 -06:00
14
+ default_executable:
15
+ dependencies: []
16
+
17
+ description: Wizard controller provides a base class (Inheriting from ActionController::Base) that provides a DSL for quickly making Wizards.
18
+ email: midwire@midwiretech.com
19
+ executables: []
20
+
21
+ extensions: []
22
+
23
+ extra_rdoc_files:
24
+ - LICENSE
25
+ - README.rdoc
26
+ files:
27
+ - .gitignore
28
+ - History.txt
29
+ - LICENSE
30
+ - README.rdoc
31
+ - Rakefile
32
+ - VERSION
33
+ - lib/wizard_controller.rb
34
+ - midwire-wizard_controller.gemspec
35
+ has_rdoc: true
36
+ homepage: http://github.com/midwire/wizard_controller
37
+ licenses: []
38
+
39
+ post_install_message:
40
+ rdoc_options:
41
+ - --charset=UTF-8
42
+ require_paths:
43
+ - lib
44
+ required_ruby_version: !ruby/object:Gem::Requirement
45
+ requirements:
46
+ - - ">="
47
+ - !ruby/object:Gem::Version
48
+ version: "0"
49
+ version:
50
+ required_rubygems_version: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: "0"
55
+ version:
56
+ requirements: []
57
+
58
+ rubyforge_project:
59
+ rubygems_version: 1.3.5
60
+ signing_key:
61
+ specification_version: 3
62
+ summary: A simple way to create non-model-based Wizards
63
+ test_files: []
64
+