radiant-reader-extension 3.0.11 → 3.0.13

Sign up to get free protection for your applications and to get access to all the features.
@@ -143,15 +143,30 @@ EOM
143
143
  end
144
144
 
145
145
  def group_options_for_select
146
- nested_set_options(Group) {|g| "#{'-' * g.level} #{g.name}" }.unshift([t("reader_extension.any_option"), nil])
146
+ options_from_tree(Group.arrange).unshift([t("reader_extension.any_option"), nil])
147
147
  end
148
148
 
149
149
  def parent_group_options_for_select(group=nil)
150
- nested_set_options(Group, group) {|g| "#{'-' * g.level} #{g.name}" }.unshift([t("reader_extension.none_option"), nil])
150
+ options_from_tree(Group.arrange, :except => group).unshift([t("reader_extension.none_option"), nil])
151
151
  end
152
152
 
153
153
  def email_link(address)
154
154
  mail_to address, nil, :encode => :hex, :replace_at => ' at ', :class => 'mailto'
155
155
  end
156
156
 
157
+ # Takes a hash of hashes in the format returned by Ancestry#arrange, returns an indented option set.
158
+ #
159
+ def options_from_tree(tree, options={})
160
+ option_list = []
161
+ depth = options[:depth] || 0
162
+ exception = options[:except]
163
+ tree.each_pair do |key, values|
164
+ unless key == exception
165
+ option_list << [". " * depth + key.name, key.id]
166
+ option_list << options_from_tree(values, :depth => depth + 1, :except => exception) if values.any?
167
+ end
168
+ end
169
+ option_list.compact
170
+ end
157
171
  end
172
+
data/app/models/group.rb CHANGED
@@ -24,10 +24,20 @@ class Group < ActiveRecord::Base
24
24
  named_scope :unsubscribable, { :conditions => "public = 0" }
25
25
 
26
26
  named_scope :find_these, lambda { |ids|
27
- ids = ['NULL'] unless ids && ids.any?
27
+ ids = [ids].flatten.compact
28
+ ids = ['NULL'] unless ids.any?
28
29
  { :conditions => ["groups.id IN (#{ids.map{"?"}.join(',')})", *ids] }
29
30
  }
30
31
 
32
+ named_scope :except, lambda { |groups|
33
+ groups = [groups].flatten.compact
34
+ if groups.any?
35
+ { :conditions => ["NOT groups.id IN (#{groups.map{"?"}.join(',')})", *groups.map(&:id)] }
36
+ else
37
+ { }
38
+ end
39
+ }
40
+
31
41
  named_scope :containing, lambda { |reader|
32
42
  {
33
43
  :joins => "INNER JOIN memberships as mb on mb.group_id = groups.id",
@@ -21,6 +21,12 @@ class Message < ActiveRecord::Base
21
21
  named_scope :ordinary, { :conditions => "function_id = '' OR function_id IS NULL" }
22
22
  named_scope :published, { :conditions => "status_id >= 100" }
23
23
 
24
+ named_scope :except, lambda { |ids|
25
+ ids = [ids].flatten.compact
26
+ ids = ['NULL'] unless ids.any?
27
+ { :conditions => ["groups.id NOT IN (#{ids.map{"?"}.join(',')})", *ids] }
28
+ }
29
+
24
30
  def filtered_body
25
31
  filter.filter(body)
26
32
  end
data/app/models/reader.rb CHANGED
@@ -5,10 +5,10 @@ require 'vcard'
5
5
  require "fastercsv"
6
6
 
7
7
  class Reader < ActiveRecord::Base
8
- @@user_columns = [:name, :email, :login, :created_at, :password, :notes]
8
+ @@user_columns = %w{name email login created_at password password_confirmation notes}
9
9
  cattr_accessor :user_columns
10
10
  cattr_accessor :current
11
- attr_accessor :email_field, :newly_activated
11
+ attr_accessor :email_field, :newly_activated, :skip_user_update
12
12
 
13
13
  acts_as_authentic do |config|
14
14
  config.validations_scope = :site_id if defined? Site
@@ -31,7 +31,7 @@ class Reader < ActiveRecord::Base
31
31
 
32
32
  validates_presence_of :name, :email
33
33
  validates_length_of :name, :maximum => 100, :allow_nil => true
34
- validates_length_of :password, :minimum => 6, :allow_nil => false, :unless => :existing_reader_keeping_password?
34
+ validates_length_of :password, :minimum => 5, :allow_nil => false, :unless => :existing_reader_keeping_password?
35
35
  # validates_format_of :password, :with => /[^A-Za-z]/, :unless => :existing_reader_keeping_password? # we have to match radiant so that users can log in both ways
36
36
  validates_confirmation_of :password, :unless => :existing_reader_keeping_password?
37
37
  validates_uniqueness_of :login, :allow_blank => true
@@ -46,8 +46,9 @@ class Reader < ActiveRecord::Base
46
46
  named_scope :active, :conditions => "activated_at IS NOT NULL"
47
47
  named_scope :inactive, :conditions => "activated_at IS NULL"
48
48
  named_scope :imported, :conditions => "old_id IS NOT NULL"
49
+
49
50
  named_scope :except, lambda { |readers|
50
- readers = [readers].flatten
51
+ readers = [readers].flatten.compact
51
52
  if readers.any?
52
53
  { :conditions => ["NOT readers.id IN (#{readers.map{"?"}.join(',')})", *readers.map(&:id)] }
53
54
  else
@@ -304,11 +305,23 @@ private
304
305
  end
305
306
 
306
307
  def update_user
307
- if self.user
308
- user_columns.each { |att| self.user.send("#{att.to_s}=", send(att)) if send("#{att.to_s}_changed?") }
309
- self.user.password_confirmation = password if password_changed?
310
- self.user.save! if self.user.changed?
308
+ if self.user && !self.skip_user_update
309
+ changed_columns = Reader.user_columns & self.changed
310
+ att = self.attributes.slice(*changed_columns)
311
+ att['password'] = self.password if self.crypted_password_changed?
312
+ self.user.send :update_with, att if att.any?
313
+ end
314
+ true
315
+ end
316
+
317
+ def update_with(att)
318
+ self.skip_user_update = true
319
+ if att['password']
320
+ att["clear_password"] = att["password_confirmation"] = att["password"]
311
321
  end
322
+ p "updating reader attributes with #{att.inspect}"
323
+ self.update_attributes(att)
324
+ self.skip_user_update = false
312
325
  end
313
326
 
314
327
  def send_group_welcomes
@@ -1,15 +1,16 @@
1
1
  - include_stylesheet 'admin/reader_group'
2
2
  - include_javascript 'admin/reader'
3
+ - groupee ||= @page
3
4
 
4
5
  - groups = Group.find(:all)
5
6
  - if groups.any?
6
7
  %p.access
7
8
  %label
8
9
  = t('reader_extension.access')
9
- - if @page.visible?
10
+ - if groupee.visible?
10
11
  = link_to t('reader_extension.access_open'), '#groups_popup', :class => 'popup unrestricted', :id => 'group_status_flag'
11
12
  - else
12
13
  = link_to t('reader_extension.access_restricted'), '#groups_popup', :class => 'popup restricted', :id => 'group_status_flag'
13
- - fields_for @page do |f|
14
+ - fields_for groupee do |f|
14
15
  = f.hidden_field :group_ids
15
16
 
@@ -1,3 +1,5 @@
1
+ - groupee ||= @page
2
+
1
3
  #groups_popup.popup{:style => "display: none"}
2
4
  #groups_busy.busy{:style => "display: none"}= image('spinner.gif', :alt => "")
3
5
  .popup_title
@@ -5,7 +7,7 @@
5
7
  %p
6
8
  = t('reader_extension.page_access_explanation')
7
9
  %form.group_selection
8
- = render :partial => 'admin/groups/chooser', :object => @page
10
+ = render :partial => 'admin/groups/chooser', :object => groupee
9
11
  .buttons
10
12
  = submit_tag t('reader_extension.set_access'), :class=>'button', :id=>'add_page_field_button'
11
13
  = t('or')
@@ -16,21 +16,18 @@
16
16
  = form.label :body
17
17
  = form.text_area :body, :class => 'textarea', :style => 'width: 100%'
18
18
 
19
- - formpart.edit_function do
20
- #message_function.set
19
+ #message_roles.set
20
+ - formpart.edit_function do
21
21
  - if admin?
22
22
  %p
23
23
  = form.label :function_id
24
24
  = form.select :function_id, MessageFunction.find_all.map { |mf| [t("message_functions.#{mf.name}"), mf.name] }, :include_blank => true
25
- %p
26
- = form.label :group_ids
27
- = render :partial => 'admin/groups/chooser', :locals => {:f => form}
28
-
29
25
  - elsif @message.new_record?
30
26
  - if @message.function
31
27
  = f.hidden_field :function_id
32
- - if @message.group_ids
33
- = f.hidden_field :group_ids
28
+
29
+ - formpart.edit_groups do
30
+ = render :partial => "admin/groups/edit_access", :locals => {:groupee => @message}
34
31
 
35
32
  - render_region :form_bottom do |form_bottom|
36
33
  - form_bottom.edit_timestamp do
@@ -41,3 +38,6 @@
41
38
  = save_model_and_continue_editing_button(@message)
42
39
  = t('or')
43
40
  = link_to t("cancel"), @message.new_record? ? admin_messages_url : admin_message_url(@message)
41
+
42
+ - form_bottom.edit_popups do
43
+ = render :partial => 'admin/groups/popup', :locals => {:groupee => @message}
@@ -5,7 +5,7 @@
5
5
  %h1 Reader configuration
6
6
 
7
7
  - main.edit_form do
8
- - form_for :config, :url => admin_reader_configuration_url, :html => {"data-onsubmit_status"=>"Saving changes&#8230;", :method => :put} do |f|
8
+ - form_for :config, :url => admin_reader_settings_url, :html => {"data-onsubmit_status"=>"Saving changes&#8230;", :method => :put} do |f|
9
9
  = render_region :form_top
10
10
  - render_region :form do |form|
11
11
  - form.edit_registration do
@@ -42,4 +42,4 @@
42
42
  %p.buttons
43
43
  %input.button{:type=>"submit", :value=>"Save Changes"}/
44
44
  or
45
- = link_to "Cancel", admin_reader_configuration_url
45
+ = link_to "Cancel", admin_reader_settings_url
@@ -6,7 +6,7 @@
6
6
  #reader_settings.box
7
7
  %h3
8
8
  .actions
9
- = button_to t("edit"), edit_admin_reader_configuration_url, :method => :get
9
+ = button_to t("edit"), edit_admin_reader_settings_url, :method => :get
10
10
  =t("reader_extension.reader_admin")
11
11
  %p.ruled
12
12
  = show_config 'reader.allow_registration?'
@@ -40,7 +40,7 @@
40
40
  %p.ruled
41
41
  %label= func.description
42
42
  - if message
43
- = link_to message.subject, admin_message_url(message)
43
+ = link_to message.subject, edit_admin_reader_settings_url(message)
44
44
  - else
45
45
  = link_to image('plus') + " create message", new_admin_message_url(:function => func), :class => 'create'
46
46
 
@@ -2,10 +2,6 @@
2
2
  - if @message
3
3
  %p
4
4
  = @message
5
- - else
6
- %p
7
- = t('reader_extension.log_in_or_register')
8
-
9
5
  = render :partial => 'login_form', :locals => {:no_title => true}
10
6
 
11
7
  - content_for :breadcrumbs do
data/config/routes.rb CHANGED
@@ -1,6 +1,7 @@
1
1
  ActionController::Routing::Routes.draw do |map|
2
2
  map.namespace :admin do |admin|
3
3
  admin.resources :readers, :except => [:show]
4
+ admin.resource :reader_settings, :controller => 'reader_configuration'
4
5
  end
5
6
 
6
7
  map.namespace :admin, :path_prefix => 'admin/readers' do |admin|
@@ -8,7 +9,6 @@ ActionController::Routing::Routes.draw do |map|
8
9
  admin.resources :groups, :has_many => [:memberships, :permissions, :group_invitations, :messages]
9
10
  admin.resources :memberships, :only => [:edit, :update], :member => [:toggle]
10
11
  admin.resources :permissions, :only => [], :member => [:toggle]
11
- admin.resource :reader_configuration, :controller => 'reader_configuration'
12
12
  end
13
13
 
14
14
  readers_prefix = Radiant.config['reader.profiles_path'] || "directory"
@@ -1,5 +1,5 @@
1
1
  module RadiantReaderExtension
2
- VERSION = '3.0.11'
2
+ VERSION = '3.0.13'
3
3
  SUMMARY = %q{Reader/viewer/visitor registration, login and access-control for Radiant CMS}
4
4
  DESCRIPTION = %q{Provides reader/member/user registration and management functions including password-reminder, group-based page access control and administrative email.}
5
5
  URL = "http://radiant.spanner.org/reader"
@@ -59,9 +59,9 @@ module ReaderAdminUI
59
59
  def load_default_message_regions
60
60
  OpenStruct.new.tap do |message|
61
61
  message.edit = Radiant::AdminUI::RegionSet.new do |edit|
62
- edit.main.concat %w{edit_header edit_form edit_footer}
63
- edit.form.concat %w{edit_subject edit_body edit_function}
64
- edit.form_bottom.concat %w{edit_timestamp edit_buttons}
62
+ edit.main.concat %w{edit_header edit_form}
63
+ edit.form.concat %w{edit_subject edit_body edit_function edit_groups}
64
+ edit.form_bottom.concat %w{edit_timestamp edit_buttons edit_popups}
65
65
  end
66
66
  message.index = Radiant::AdminUI::RegionSet.new do |index|
67
67
  index.thead.concat %w{subject_header function_header groups_header sent_header modify_header}
data/lib/reader_user.rb CHANGED
@@ -1,18 +1,35 @@
1
1
  module ReaderUser
2
2
 
3
3
  def self.included(base)
4
+ extend ClassMethods
4
5
  base.class_eval do
5
- has_one :reader
6
- before_update :update_reader
6
+ has_one :reader, :dependent => :nullify
7
+ attr_accessor :skip_reader_update
8
+ include InstanceMethods
9
+ before_save :update_reader # there is already a before_update call that hashes the password, so we need to come in before that
7
10
  end
8
11
  end
12
+
13
+ module ClassMethods
14
+
15
+ end
9
16
 
10
- def update_reader
11
- if self.reader
12
- Reader.user_columns.each { |att| self.reader.send("#{att.to_s}=", send(att)) if send("#{att.to_s}_changed?") }
13
- self.reader.password_confirmation = password if password_changed?
14
- self.reader.save! if self.reader.changed?
17
+ module InstanceMethods
18
+ def update_reader
19
+ if !new_record? && self.reader && !self.skip_reader_update
20
+ changed_columns = Reader.user_columns & self.changed
21
+ att = self.attributes.slice(*changed_columns)
22
+ self.reader.send :update_with, att if att.any?
23
+ end
24
+ true
25
+ end
26
+
27
+ def update_with(att)
28
+ self.skip_reader_update = true
29
+ self.confirm_password = false
30
+ p "updating user attributes with #{att.inspect}"
31
+ self.update_attributes(att)
32
+ self.skip_reader_update = false
15
33
  end
16
34
  end
17
-
18
35
  end
@@ -8,9 +8,9 @@ module SiteControllerExtensions
8
8
  def find_page_with_group_check(url)
9
9
  page = find_page_without_group_check(url)
10
10
  if page
11
- raise ReaderError::LoginRequired, t("reader_extension.page_is_private_please_log_in") if page.restricted? && !current_reader
12
- raise ReaderError::ActivationRequired, t("reader_extension.page_is_private_please_log_in") if page.restricted? && !current_reader.activated?
13
- raise ReaderError::AccessDenied, t("reader_extension.page_access_not_given") unless page.visible_to?(current_reader)
11
+ raise ReaderError::LoginRequired, t("reader_extension.page_not_public") if page.restricted? && !current_reader
12
+ raise ReaderError::ActivationRequired, t("reader_extension.page_not_public") if page.restricted? && !current_reader.activated?
13
+ raise ReaderError::AccessDenied, t("reader_extension.page_permission_denied") unless page.visible_to?(current_reader)
14
14
  end
15
15
  page
16
16
  end
@@ -32,9 +32,9 @@ Gem::Specification.new do |s|
32
32
  s.require_paths = ["lib"]
33
33
 
34
34
  s.post_install_message = %{
35
- Add this to your radiant project with:
35
+ Add this to your radiant project with a line in your Gemfile:
36
36
 
37
- config.gem 'radiant-reader-extension', :version => '~> #{RadiantReaderExtension::VERSION}'
37
+ gem 'radiant-reader-extension', '~> #{RadiantReaderExtension::VERSION}'
38
38
 
39
39
  and if you haven't already, remember to enable ActionMailer in your
40
40
  project's config/environment.rb.
data/reader_extension.rb CHANGED
@@ -24,8 +24,8 @@ class ReaderExtension < Radiant::Extension
24
24
  Radiant::AdminUI.load_reader_extension_regions
25
25
  end
26
26
 
27
- admin.page.edit.add :layout, "page_groups"
28
- admin.page.edit.add :main, "groups_popup", :after => 'edit_popups'
27
+ admin.page.edit.add :layout, "admin/groups/edit_access"
28
+ admin.page.edit.add :main, "admin/groups/popup", :after => 'edit_popups'
29
29
  admin.page.index.add :sitemap_head, "groups_column_header", :after => 'status_column_header'
30
30
  admin.page.index.add :node, "groups_column", :after => 'status_column'
31
31
 
@@ -33,10 +33,10 @@ class ReaderExtension < Radiant::Extension
33
33
  add_item("Readers", "/admin/readers")
34
34
  add_item("Groups", "/admin/readers/groups")
35
35
  add_item("Messages", "/admin/readers/messages")
36
- add_item("Settings", "/admin/readers/reader_configuration")
36
+ add_item("Settings", "/admin/reader_settings")
37
37
  end
38
38
  tab("Settings") do
39
- add_item("Readers", "/admin/readers/reader_configuration")
39
+ add_item("Readers", "/admin/reader_settings")
40
40
  end
41
41
  end
42
42
  end
@@ -23,7 +23,7 @@ describe ReaderActivationsController do
23
23
 
24
24
  it "should redirect to the dashboard" do
25
25
  response.should be_redirect
26
- response.should redirect_to(dashboard_url)
26
+ response.should redirect_to(reader_dashboard_url)
27
27
  end
28
28
  end
29
29
 
@@ -17,15 +17,14 @@ describe User do
17
17
  user.name = "Cardinal Fang"
18
18
  user.save!
19
19
  user.reader.name.should == "Cardinal Fang"
20
- Reader.find_by_name("Cardinal Fang").should == readers(:user)
21
20
  end
22
21
 
23
22
  it "should update the associated reader's credentials" do
24
- user.password = user.password_confirmation = 'bl0tto'
23
+ user.password = 'bl0tto'
24
+ user.password_confirmation = 'bl0tto'
25
25
  user.save!
26
26
  user.authenticated?('bl0tto').should be_true
27
27
  user.reader.valid_password?('bl0tto').should be_true
28
- # ReaderSession.new(:login => reader.login, :password => 'bl0tto').should be_valid
29
28
  end
30
29
  end
31
30
  end
@@ -99,20 +99,17 @@ describe Reader do
99
99
  end
100
100
 
101
101
  describe "on update if really a user" do
102
-
103
102
  it "should update the user's attributes" do
104
103
  reader = readers(:user)
105
104
  reader.name = "Cardinal Fang"
106
105
  reader.save!
107
-
108
- User.find_by_name("Cardinal Fang").should == users(:existing)
106
+ reader.user.name.should == "Cardinal Fang"
109
107
  end
110
108
 
111
109
  it "should update the user's credentials" do
112
110
  reader = readers(:user)
113
111
  reader.password = reader.password_confirmation = 'bl0tto'
114
112
  reader.save!
115
- ReaderSession.new(:login => reader.login, :password => 'bl0tto').should be_valid
116
113
  reader.user.authenticated?('bl0tto').should be_true
117
114
  end
118
115
  end
data/spec/spec.opts CHANGED
@@ -1,6 +1,4 @@
1
1
  --colour
2
- --format
3
- profile
4
- --loadby
5
- mtime
2
+ --format specdoc
3
+ --loadby mtime
6
4
  --reverse
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: radiant-reader-extension
3
3
  version: !ruby/object:Gem::Version
4
- hash: 17
4
+ hash: 29
5
5
  prerelease:
6
6
  segments:
7
7
  - 3
8
8
  - 0
9
- - 11
10
- version: 3.0.11
9
+ - 13
10
+ version: 3.0.13
11
11
  platform: ruby
12
12
  authors:
13
13
  - William Ross
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-10-05 00:00:00 Z
18
+ date: 2011-10-11 00:00:00 Z
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency
21
21
  name: radiant-layouts-extension
@@ -198,9 +198,11 @@ files:
198
198
  - app/views/admin/group_invitations/preview.html.haml
199
199
  - app/views/admin/groups/_add_readers.html.haml
200
200
  - app/views/admin/groups/_chooser.html.haml
201
+ - app/views/admin/groups/_edit_access.html.haml
201
202
  - app/views/admin/groups/_form.html.haml
202
203
  - app/views/admin/groups/_group.html.haml
203
204
  - app/views/admin/groups/_list_head.html.haml
205
+ - app/views/admin/groups/_popup.html.haml
204
206
  - app/views/admin/groups/edit.html.haml
205
207
  - app/views/admin/groups/index.html.haml
206
208
  - app/views/admin/groups/new.html.haml
@@ -220,9 +222,7 @@ files:
220
222
  - app/views/admin/messages/show.html.haml
221
223
  - app/views/admin/pages/_groups_column.html.haml
222
224
  - app/views/admin/pages/_groups_column_header.html.haml
223
- - app/views/admin/pages/_groups_popup.html.haml
224
225
  - app/views/admin/pages/_listed.html.haml
225
- - app/views/admin/pages/_page_groups.html.haml
226
226
  - app/views/admin/permissions/_page.html.haml
227
227
  - app/views/admin/reader_configuration/edit.html.haml
228
228
  - app/views/admin/reader_configuration/show.html.haml
@@ -328,10 +328,7 @@ files:
328
328
  - public/stylesheets/sass/admin/reader.sass
329
329
  - public/stylesheets/sass/admin/reader_group.sass
330
330
  - public/stylesheets/sass/reader.sass
331
- - radiant-reader-extension-3.0.10.gem
332
- - radiant-reader-extension-3.0.7.gem
333
- - radiant-reader-extension-3.0.8.gem
334
- - radiant-reader-extension-3.0.9.gem
331
+ - radiant-reader-extension-3.0.13.gem
335
332
  - radiant-reader-extension.gemspec
336
333
  - Rakefile
337
334
  - reader_extension.rb
@@ -360,7 +357,7 @@ files:
360
357
  homepage: http://radiant.spanner.org/reader
361
358
  licenses: []
362
359
 
363
- post_install_message: "\n Add this to your radiant project with:\n\n config.gem 'radiant-reader-extension', :version => '~> 3.0.11'\n\n and if you haven't already, remember to enable ActionMailer in your\n project's config/environment.rb.\n "
360
+ post_install_message: "\n Add this to your radiant project with a line in your Gemfile:\n\n gem 'radiant-reader-extension', '~> 3.0.13'\n\n and if you haven't already, remember to enable ActionMailer in your\n project's config/environment.rb.\n "
364
361
  rdoc_options: []
365
362
 
366
363
  require_paths:
Binary file
Binary file
Binary file
Binary file