hobo 0.6 → 0.6.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (39) hide show
  1. data/bin/hobo +2 -3
  2. data/hobo_files/plugin/CHANGES.txt +139 -0
  3. data/hobo_files/plugin/generators/hobo_front_controller/hobo_front_controller_generator.rb +1 -8
  4. data/hobo_files/plugin/generators/hobo_front_controller/templates/controller.rb +1 -39
  5. data/hobo_files/plugin/generators/hobo_front_controller/templates/index.dryml +2 -2
  6. data/hobo_files/plugin/generators/hobo_migration/hobo_migration_generator.rb +27 -7
  7. data/hobo_files/plugin/generators/hobo_rapid/templates/hobo_rapid.js +1 -2
  8. data/hobo_files/plugin/generators/hobo_user_controller/USAGE +34 -0
  9. data/hobo_files/plugin/generators/hobo_user_controller/hobo_user_controller_generator.rb +43 -0
  10. data/hobo_files/plugin/generators/hobo_user_controller/templates/controller.rb +5 -0
  11. data/hobo_files/plugin/generators/hobo_user_controller/templates/functional_test.rb +18 -0
  12. data/hobo_files/plugin/generators/hobo_user_controller/templates/helper.rb +2 -0
  13. data/hobo_files/plugin/generators/hobo_user_controller/templates/view.rhtml +2 -0
  14. data/hobo_files/plugin/init.rb +6 -2
  15. data/hobo_files/plugin/lib/extensions.rb +28 -41
  16. data/hobo_files/plugin/lib/hobo.rb +37 -17
  17. data/hobo_files/plugin/lib/hobo/authentication_support.rb +25 -10
  18. data/hobo_files/plugin/lib/hobo/composite_model.rb +2 -2
  19. data/hobo_files/plugin/lib/hobo/controller.rb +8 -34
  20. data/hobo_files/plugin/lib/hobo/dryml/dryml_builder.rb +1 -1
  21. data/hobo_files/plugin/lib/hobo/dryml/part_context.rb +103 -0
  22. data/hobo_files/plugin/lib/hobo/dryml/template.rb +10 -11
  23. data/hobo_files/plugin/lib/hobo/dryml/template_environment.rb +29 -72
  24. data/hobo_files/plugin/lib/hobo/hobo_helper.rb +11 -10
  25. data/hobo_files/plugin/lib/hobo/migrations.rb +12 -0
  26. data/hobo_files/plugin/lib/hobo/model.rb +3 -3
  27. data/hobo_files/plugin/lib/hobo/model_controller.rb +3 -3
  28. data/hobo_files/plugin/lib/hobo/rapid_helper.rb +3 -3
  29. data/hobo_files/plugin/lib/hobo/user_controller.rb +80 -0
  30. data/hobo_files/plugin/tags/rapid.dryml +36 -20
  31. data/hobo_files/plugin/tags/rapid_editing.dryml +4 -5
  32. data/hobo_files/plugin/tags/rapid_forms.dryml +6 -6
  33. data/hobo_files/plugin/tags/rapid_navigation.dryml +7 -5
  34. data/hobo_files/plugin/tags/rapid_pages.dryml +116 -10
  35. data/hobo_files/plugin/tags/rapid_support.dryml +23 -0
  36. metadata +13 -5
  37. data/hobo_files/plugin/generators/hobo_front_controller/templates/login.dryml +0 -42
  38. data/hobo_files/plugin/generators/hobo_front_controller/templates/signup.dryml +0 -43
  39. data/hobo_files/plugin/lib/hobo/mapping_tags.rb +0 -262
data/bin/hobo CHANGED
@@ -86,10 +86,9 @@ Dir.chdir(app_path) do
86
86
  if user_model
87
87
  puts "\nCreating #{user_model} model and controller...\n"
88
88
  command("#{gen} hobo_user_model #{user_model}")
89
- command("#{gen} hobo_model_controller #{user_model}")
89
+ command("#{gen} hobo_user_controller #{user_model}")
90
90
  end
91
91
 
92
92
  puts "\nCreating standard pages...\n"
93
- command("#{gen} hobo_front_controller front " +
94
- "#{'--no-user' unless user_model} --delete-index --add-routes")
93
+ command("#{gen} hobo_front_controller front --delete-index --add-routes")
95
94
  end
@@ -1,3 +1,142 @@
1
+ === Release 0.6.1 ===
2
+
3
+ Multiple user models
4
+
5
+ Hobo now supports multiple user models, with independent sign-up /
6
+ log-in/out for each.
7
+
8
+ The controller needs to declare hobo_user_controller instead of
9
+ hobo_model_controller (it still has all the hobo_model_controller
10
+ features). e.g.
11
+
12
+ class AdminsController; hobo_user_controller; end
13
+
14
+ Hobo routing will automatically give you
15
+
16
+ /admin_login
17
+ /admin_logout
18
+ /admin_signup
19
+
20
+ Note this controller will now filter loggin of passwords.
21
+
22
+ The model needs to include Hobo::AuthenticatedUser and declare a
23
+ login attribute with, e.g.
24
+
25
+ set_login_attr :email
26
+
27
+ The hobo_front_controller generator no longer generates anything
28
+ related to users - it's now just the fron page and search page.
29
+
30
+ There is a new hobo_user_model generator to create these
31
+ controllers.
32
+
33
+ The global value Hobo.user_model is gone
34
+
35
+ Rapid now has <LoginPage> and <SignupPage> templates. They're not so
36
+ customisable just now but you can of course replace them completely
37
+ with your own views.
38
+
39
+
40
+ Misc fixes
41
+
42
+ Search was broken
43
+
44
+ The 'hobo' command tried to connect to the DB, which was a problem
45
+ as you'd had no chance to configure database.yml
46
+
47
+
48
+ Rapid
49
+
50
+ Fix: reset_form and refocus form options
51
+
52
+ <Table> now supports @fields, allowing you to give a bunch of field
53
+ names and automatically have a table with a column for each of those
54
+ fields. There's also a <controls> param that can be used to have a
55
+ delete button and edit link on each row. As usual there's a ton of
56
+ customisation options - see the source.
57
+
58
+ <human_type> is now <type_name> and takes flags @plural and @lowercase
59
+
60
+ <editor> and <input> have better automatic css classes
61
+
62
+ Restored old behaviour where <page_nav/> would display nothing when
63
+ there's only one page.
64
+
65
+ Finally created <EditPage>
66
+
67
+ Small cleanups in the rapid pages
68
+
69
+ New tag <with_field_names/> used in <Table> to iterate over the
70
+ column headings.
71
+
72
+ <view> for Time objects now supports @format - a strftime style
73
+ format string.
74
+
75
+
76
+
77
+ Migration generator
78
+
79
+ Fix: Edge Rails now dumps out in sexy format, which was freaking the
80
+ migration generator.
81
+
82
+ You can now configure the generator to completely ignore specified
83
+ tables and models. In environment.rb do
84
+
85
+ Hobo::Migrations.ignore = %w(red_fish blue_fish)
86
+
87
+ That will ignore the models RedFish and BlueFish, and the tables
88
+ red_fishes and blue_fishes
89
+
90
+ To ignore just tables, assign an array of their names to
91
+
92
+ Hobo::Migrations.ignore_tables
93
+
94
+ To ignore just models, assign an array of the class names to
95
+
96
+ Hobo::Migrations.ignore_models
97
+
98
+ New secure ajax parts mechanism
99
+
100
+ The new mechanism stores the part state in a base 64 encoded string,
101
+ complete with an SHA1 (by default) digest, so malicious tampering
102
+ with the part state is prevented.
103
+
104
+ Parts can now capture the state of local variables along with the
105
+ DRYML context. Give a list of locals you wish to capture in the
106
+ 'part_locals' attribute. e.g.
107
+
108
+ <div part="my_part" part_locals="a, b"> ... </div>
109
+
110
+ (the inability to do this was a serious limitation of the previous
111
+ mechanism)
112
+
113
+
114
+ Core extensions
115
+
116
+ Added Methodphitamine and removed omap, oselect, ofind, oany oall.
117
+
118
+ See http://jicksta.com/articles/2007/08/04/the-methodphitamine
119
+
120
+
121
+ DRYML
122
+
123
+ merge_attrs fixed to not complain about nils
124
+
125
+ Fix: css classes were not accumulated in some template parameter
126
+ situations
127
+
128
+
129
+ Hobo module
130
+
131
+ #type_name renamed to #type_id
132
+
133
+ #object_from_dom_id will now return classes when the id has no, er, id. As in
134
+
135
+ Hobo.object_from_dom_id("blog_post") #=> BlogPost
136
+
137
+ Similarly, #dom_id generates those kind of ID for classes
138
+
139
+
1
140
  === Release 0.6 ===
2
141
 
3
142
  DRYML
@@ -34,7 +34,7 @@ class HoboFrontControllerGenerator < Rails::Generator::NamedBase
34
34
  File.join('app/helpers', class_path, "#{file_name}_helper.rb"))
35
35
 
36
36
 
37
- pages = options[:no_user] ? %w{index search} : %w{index search login signup}
37
+ pages = options[:no_user] ? %w{index search} : %w{index search}
38
38
  for page in pages
39
39
  m.template("#{page}.dryml", File.join('app/views', class_path, file_name, "#{page}.dryml"))
40
40
  end
@@ -51,11 +51,6 @@ class HoboFrontControllerGenerator < Rails::Generator::NamedBase
51
51
 
52
52
  route = (" map.search 'search', :controller => '#{name}', :action => 'search'\n" +
53
53
  " map.homepage '', :controller => '#{name}', :action => 'index'")
54
- unless options[:no_user]
55
- route += ("\n map.login 'login', :controller => '#{name}', :action => 'login'\n" +
56
- " map.logout 'logout', :controller => '#{name}', :action => 'logout'\n" +
57
- " map.signup 'signup', :controller => '#{name}', :action => 'signup'")
58
- end
59
54
 
60
55
  route_src = File.read(routes_path)
61
56
  return if route_src.include?(route)
@@ -81,8 +76,6 @@ class HoboFrontControllerGenerator < Rails::Generator::NamedBase
81
76
  opt.separator 'Options:'
82
77
  opt.on("--add-routes",
83
78
  "Modify config/routes.rb to support the front controller") { |v| options[:add_routes] = true }
84
- opt.on("--no-user",
85
- "Don't create the login and signup pages") { |v| options[:no_user] = true }
86
79
  opt.on("--delete-index",
87
80
  "Delete public/index.html") { |v| options[:delete_index] = true }
88
81
  end
@@ -2,50 +2,12 @@ class <%= class_name %>Controller < ApplicationController
2
2
 
3
3
  hobo_controller
4
4
 
5
- filter_parameter_logging "password"
6
-
7
5
  def index; end
8
6
 
9
7
  def search
10
- if request.post?
8
+ if params[:query]
11
9
  site_search(params[:query])
12
10
  end
13
11
  end
14
12
 
15
- def login
16
- return unless request.post?
17
- user = Hobo.user_model.authenticate(params[:login], params[:password])
18
- if user
19
- self.current_user = user
20
- if params[:remember_me] == "1"
21
- self.current_user.remember_me
22
- cookies[:auth_token] = { :value => self.current_user.remember_token ,
23
- :expires => self.current_user.remember_token_expires_at }
24
- end
25
- redirect_back_or_default(:action => 'index')
26
- flash[:notice] = "You have logged in"
27
- else
28
- flash[:notice] = "You did not provide a valid login and password"
29
- end
30
- end
31
-
32
- def signup
33
- @user = Hobo.user_model.new(params[:user])
34
- return unless request.post?
35
- @user.save!
36
- self.current_user = @user
37
- redirect_back_or_default(:action => 'index')
38
- flash[:notice] = "Thanks for signing up!"
39
- rescue ActiveRecord::RecordInvalid
40
- render :action => 'signup'
41
- end
42
-
43
- def logout
44
- self.current_user.forget_me if logged_in?
45
- cookies.delete :auth_token
46
- reset_session
47
- flash[:notice] = "You have been logged out."
48
- redirect_back_or_default(:action => 'index')
49
- end
50
-
51
13
  end
@@ -19,8 +19,8 @@
19
19
  <section>
20
20
  <if test="&this.count == 0">
21
21
  <p>There are no <%%= this.name.titleize.pluralize %></p>
22
- <if test="&can_create?(this) and this != Hobo.user_model">
23
- <p>Create a <a to="&this.new"/>.</p>
22
+ <if test="&can_create?(this)">
23
+ <p>Create a <a to="&this" action="new"/>.</p>
24
24
  </if>
25
25
  </if>
26
26
  <else>
@@ -15,13 +15,19 @@ class HoboMigrationGenerator < Rails::Generator::Base
15
15
  # Force load of hobo models
16
16
  Hobo.models
17
17
 
18
+ ignore_tables = Hobo::Migrations.ignore_tables + Hobo::Migrations.ignore.every(:pluralize)
19
+ ignore_models = (Hobo::Migrations.ignore + Hobo::Migrations.ignore_models).every(:underscore)
20
+
21
+ db_tables = connection.tables - ignore_tables
22
+
18
23
  models = ActiveRecord::Base.send(:subclasses).reject {|c| c.name.starts_with?("CGI::") }
24
+ models = models.reject {|m| m.name.underscore.in?(ignore_models) }
19
25
  table_models = models.index_by {|m| m.table_name}
20
26
  model_table_names = models.every(:table_name)
21
27
 
22
- to_create = model_table_names - connection.tables
23
- to_drop = connection.tables - model_table_names - ['schema_info']
24
- to_change = connection.tables & model_table_names
28
+ to_create = model_table_names - db_tables
29
+ to_drop = db_tables - model_table_names - ['schema_info']
30
+ to_change = db_tables & model_table_names
25
31
 
26
32
  to_rename = rename_or_drop!(to_create, to_drop, "table")
27
33
 
@@ -54,8 +60,8 @@ class HoboMigrationGenerator < Rails::Generator::Base
54
60
  undo_changes << undo
55
61
  end
56
62
 
57
- up = [renames, drops, creates, changes * "\n\n"].select{|s|!s.blank?} * "\n\n"
58
- down = [undo_renames, undo_drops, undo_creates, undo_changes * "\n\n"].select{|s|!s.blank?} * "\n\n"
63
+ up = [renames, drops, creates, changes].flatten.select{|s|!s.blank?} * "\n\n"
64
+ down = [undo_renames, undo_drops, undo_creates, undo_changes].flatten.select{|s|!s.blank?} * "\n\n"
59
65
 
60
66
  puts "\n---------- Up Migration ----------", up, "----------------------------------"
61
67
  puts "\n---------- Down Migration --------", down, "----------------------------------"
@@ -210,14 +216,28 @@ class HoboMigrationGenerator < Rails::Generator::Base
210
216
  res.string.strip.gsub("\n ", "\n")
211
217
  end
212
218
 
219
+ def column_options_from_reverted_table(table, column)
220
+ revert = revert_table(table)
221
+ if (md = revert.match(/\s*t\.column\s+"#{column}",\s+(:[a-zA-Z0-9_]+)(?:,\s+(.*?)$)?/m))
222
+ # Ugly migration
223
+ _, type, options = *md
224
+ elsif (md = revert.match(/\s*t\.([a-z_]+)\s+"#{column}"(?:,\s+(.*?)$)?/m))
225
+ # Sexy migration
226
+ _, type, options = *md
227
+ type = ":#{type}"
228
+ end
229
+ [type, options]
230
+ end
231
+
213
232
 
214
233
  def change_column_back(table, column)
215
- _, type, options = *revert_table(table).match(/\s*t\.column\s+"#{column}",\s+(:[a-zA-Z0-9_]+)(?:,\s+(.*?)$)?/m)
234
+ type, options = column_options_from_reverted_table(table, column)
216
235
  "change_column :#{table}, :#{column}, #{type}#{', ' + options.strip if options}"
217
236
  end
218
237
 
219
238
  def revert_column(table, column)
220
- "add_column :#{table}, :#{column}, " + revert_table(table).match(/\s*t\.column\s+"#{column}",\s+(.*?)$/m)[1].strip
239
+ type, options = column_options_from_reverted_table(table, column)
240
+ "add_column :#{table}, :#{column}, #{type}#{', ' + options.strip if options}"
221
241
  end
222
242
 
223
243
 
@@ -48,9 +48,8 @@ var Hobo = {
48
48
  if (updates.length > 0) {
49
49
  updates.each(function(dom_id) {
50
50
  if (!hoboParts[dom_id]) { throw "Update of dom-id that is not a part: " + dom_id }
51
- params.push("render["+i+"][part]=" + hoboParts[dom_id][0])
51
+ params.push("render["+i+"][part_context]=" + hoboParts[dom_id])
52
52
  params.push("render["+i+"][id]=" + dom_id)
53
- params.push("render["+i+"][object]=" + hoboParts[dom_id][1])
54
53
  i += 1
55
54
  })
56
55
  params.push("part_page=" + hoboPartPage)
@@ -0,0 +1,34 @@
1
+ Description:
2
+
3
+ The controller generator creates a controller geared up to handle
4
+ login and signup for a specific user model. It can also be used as
5
+ a regular hobo_model_controller.
6
+
7
+ The generator takes a controller name and a list of views as
8
+ arguments. The controller name may be given in CamelCase or
9
+ under_score and should not be suffixed with 'Controller'. To
10
+ create a controller within a module, specify the controller name
11
+ as 'module/controller'.
12
+
13
+ The generator creates a controller class in app/controllers with view
14
+ templates in app/views/controller_name, a helper class in app/helpers,
15
+ and a functional test suite in test/functional.
16
+
17
+ Example:
18
+ ./script/generate controller CreditCard open debit credit close
19
+
20
+ Credit card controller with URLs like /credit_card/debit.
21
+ Controller: app/controllers/credit_card_controller.rb
22
+ Views: app/views/credit_card/debit.rhtml [...]
23
+ Helper: app/helpers/credit_card_helper.rb
24
+ Test: test/functional/credit_card_controller_test.rb
25
+
26
+ Modules Example:
27
+ ./script/generate hobo_user_controller 'admin/credit_card' suspend late_fee
28
+
29
+ Credit card admin controller with URLs /admin/credit_card/suspend.
30
+ Controller: app/controllers/admin/credit_card_controller.rb
31
+ Views: app/views/admin/credit_card/debit.rhtml [...]
32
+ Helper: app/helpers/admin/credit_card_helper.rb
33
+ Test: test/functional/admin/credit_card_controller_test.rb
34
+
@@ -0,0 +1,43 @@
1
+ class HoboUserControllerGenerator < Rails::Generator::NamedBase
2
+
3
+ def initialize(args, options)
4
+ args[0] = args[0].pluralize
5
+ super(args, options)
6
+ end
7
+
8
+ def manifest
9
+ record do |m|
10
+ # Check for class naming collisions.
11
+ m.class_collisions class_path, "#{class_name}Controller", "#{class_name}ControllerTest", "#{class_name}Helper"
12
+
13
+ # Controller, helper, views, and test directories.
14
+ m.directory File.join('app/controllers', class_path)
15
+ m.directory File.join('app/helpers', class_path)
16
+ m.directory File.join('app/views', class_path, file_name)
17
+ m.directory File.join('test/functional', class_path)
18
+
19
+ # Controller class, functional test, and helper class.
20
+ m.template 'controller.rb',
21
+ File.join('app/controllers',
22
+ class_path,
23
+ "#{file_name}_controller.rb")
24
+
25
+ m.template 'functional_test.rb',
26
+ File.join('test/functional',
27
+ class_path,
28
+ "#{file_name}_controller_test.rb")
29
+
30
+ m.template 'helper.rb',
31
+ File.join('app/helpers',
32
+ class_path,
33
+ "#{file_name}_helper.rb")
34
+
35
+ # View template for each action.
36
+ actions.each do |action|
37
+ path = File.join('app/views', class_path, file_name, "#{action}.rhtml")
38
+ m.template 'view.rhtml', path,
39
+ :assigns => { :action => action, :path => path }
40
+ end
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,5 @@
1
+ class <%= class_name %>Controller < ApplicationController
2
+
3
+ hobo_user_controller
4
+
5
+ end
@@ -0,0 +1,18 @@
1
+ require File.dirname(__FILE__) + '<%= '/..' * class_nesting_depth %>/../test_helper'
2
+ require '<%= file_path %>_controller'
3
+
4
+ # Re-raise errors caught by the controller.
5
+ class <%= class_name %>Controller; def rescue_action(e) raise e end; end
6
+
7
+ class <%= class_name %>ControllerTest < Test::Unit::TestCase
8
+ def setup
9
+ @controller = <%= class_name %>Controller.new
10
+ @request = ActionController::TestRequest.new
11
+ @response = ActionController::TestResponse.new
12
+ end
13
+
14
+ # Replace this with your real tests.
15
+ def test_truth
16
+ assert true
17
+ end
18
+ end
@@ -0,0 +1,2 @@
1
+ module <%= class_name %>Helper
2
+ end
@@ -0,0 +1,2 @@
1
+ <h1><%= class_name %>#<%= action %></h1>
2
+ <p>Find me in <%= path %></p>
@@ -24,6 +24,12 @@ ActionView::Base.register_template_handler("dryml", Hobo::Dryml::TemplateHandler
24
24
 
25
25
  class ActionController::Base
26
26
 
27
+ def self.hobo_user_controller(model=nil)
28
+ include Hobo::ModelController
29
+ self.model = model if model
30
+ include Hobo::UserController
31
+ end
32
+
27
33
  def self.hobo_model_controller(model=nil)
28
34
  include Hobo::ModelController
29
35
  self.model = model if model
@@ -43,6 +49,4 @@ end
43
49
 
44
50
  # Default settings
45
51
 
46
- Hobo.user_model ||= (User rescue (Person rescue nil))
47
-
48
52
  Hobo.developer_features = ["development", "test"].include?(RAILS_ENV) if Hobo.developer_features? == nil