card 1.16.12 → 1.16.13

Sign up to get free protection for your applications and to get access to all the features.
Files changed (43) hide show
  1. checksums.yaml +4 -4
  2. data/VERSION +1 -1
  3. data/card.gemspec +1 -1
  4. data/db/migrate_core_cards/20130823192433_add_style_cards.rb +39 -24
  5. data/db/migrate_core_cards/20140629222005_add_email_cards.rb +6 -11
  6. data/db/migrate_core_cards/20151120180631_add_token_expiration.rb +7 -0
  7. data/db/seed/new/card_actions.yml +396 -388
  8. data/db/seed/new/card_acts.yml +1 -595
  9. data/db/seed/new/card_changes.yml +8154 -23619
  10. data/db/seed/new/card_references.yml +1009 -988
  11. data/db/seed/new/cards.yml +1445 -1423
  12. data/db/seed/test/fixtures/card_actions.yml +1375 -1399
  13. data/db/seed/test/fixtures/card_acts.yml +445 -1063
  14. data/db/seed/test/fixtures/card_changes.yml +11440 -26881
  15. data/db/seed/test/fixtures/card_references.yml +1523 -1502
  16. data/db/seed/test/fixtures/cards.yml +2736 -2715
  17. data/db/seed/test/seed.rb +7 -10
  18. data/db/version_core_cards.txt +1 -1
  19. data/lib/card/auth.rb +65 -19
  20. data/lib/card/cache.rb +18 -18
  21. data/lib/card/env.rb +10 -10
  22. data/lib/card/format.rb +41 -30
  23. data/lib/card/location.rb +3 -5
  24. data/lib/card/subcards.rb +0 -3
  25. data/lib/card/success.rb +14 -11
  26. data/mod/01_core/set/all/subcards.rb +4 -2
  27. data/mod/01_core/set/all/trash.rb +4 -1
  28. data/mod/02_basic_types/set/type/pointer.rb +5 -2
  29. data/mod/05_email/set/all/notify.rb +85 -73
  30. data/mod/05_email/spec/set/all/notify_spec.rb +74 -55
  31. data/mod/05_standard/set/all/comment.rb +18 -12
  32. data/mod/05_standard/set/all/error.rb +5 -1
  33. data/mod/05_standard/set/right/account.rb +50 -73
  34. data/mod/05_standard/set/right/token.rb +49 -2
  35. data/mod/05_standard/set/self/signin.rb +14 -12
  36. data/mod/05_standard/set/type/signup.rb +17 -21
  37. data/mod/05_standard/spec/set/all/account_spec.rb +1 -1
  38. data/mod/05_standard/spec/set/right/account_spec.rb +76 -52
  39. data/mod/05_standard/spec/set/right/password_spec.rb +10 -11
  40. data/mod/05_standard/spec/set/right/token_spec.rb +19 -1
  41. data/mod/05_standard/spec/set/type/signup_spec.rb +3 -4
  42. data/spec/lib/card/auth_spec.rb +46 -5
  43. metadata +5 -4
@@ -2,19 +2,17 @@
2
2
  require 'timecop'
3
3
 
4
4
  class SharedData
5
- #attr_accessor :users
6
5
  USERS = [
7
- 'Joe User', 'Joe Admin', 'Joe Camel', 'Sample User', 'No count',
8
- 'u1', 'u2', 'u3',
9
- 'Big Brother', 'Optic fan', 'Sunglasses fan', 'Narcissist'
10
- ]
6
+ 'Joe User', 'Joe Admin', 'Joe Camel', 'Sample User', 'No count',
7
+ 'u1', 'u2', 'u3',
8
+ 'Big Brother', 'Optic fan', 'Sunglasses fan', 'Narcissist'
9
+ ]
11
10
 
12
11
  def self.account_args hash
13
- { "+*account" => { "+*password" =>'joe_pass' }.merge( hash ) }
12
+ { "+*account" => { "+*password" => 'joe_pass' }.merge(hash) }
14
13
  end
15
14
 
16
15
  def self.add_test_data
17
-
18
16
  Card::Cache.reset_global
19
17
  Card::Env.reset
20
18
  Card::Auth.as_bot
@@ -52,13 +50,12 @@ class SharedData
52
50
  #above still necessary? try commenting out above and 'Sign up' below
53
51
  Card::Auth.current_id = Card::WagnBotID # need to reset after creating sign up, which changes current_id for extend phase
54
52
 
53
+ no_samples = %( user sign_up set number list listed_by )
55
54
  Card::Auth.createable_types.each do |type|
56
- next if ['User', 'Sign up', 'Set', 'Number', 'List', 'Listed by'].include? type
55
+ next if no_samples.include? type.to_name.key
57
56
  Card.create! type: type, name: "Sample #{type}"
58
57
  end
59
58
 
60
-
61
-
62
59
  # data for role_test.rb
63
60
 
64
61
  Card.create! name: 'u1', type_code: 'user', subcards: account_args('+*email'=>'u1@user.com', '+*password'=>'u1_pass')
@@ -1 +1 @@
1
- 20150910085603
1
+ 20151120180631
@@ -13,33 +13,67 @@ class Card
13
13
  class << self
14
14
  # Authenticates a user by their login name and unencrypted password.
15
15
  def authenticate email, password
16
- accounted = Auth[email]
17
- return unless accounted && (account = accounted.account) &&
18
- account.active?
19
- if Card.config.no_authentication ||
20
- password_authenticated?(account, password.strip)
21
- accounted.id
16
+ account = Auth[email]
17
+ case
18
+ when !account then nil
19
+ when !account.active? then nil
20
+ when Card.config.no_authentication then account
21
+ when password_valid?(account, password.strip) then account
22
22
  end
23
23
  end
24
24
 
25
- def password_authenticated? account, password
25
+ def password_valid? account, password
26
26
  account.password == encrypt(password, account.salt)
27
27
  end
28
28
 
29
+ def set_current_from_token token, current=nil
30
+ account = find_by_token token
31
+ if account && account.validate_token!(token)
32
+ unless current && always_ok_usr_id?(account.left_id)
33
+ current = account.left_id
34
+ end
35
+ set_current_from_mark current
36
+ elsif Env.params[:live_token]
37
+ true
38
+ # Used for activations and resets.
39
+ # Continue as anonymous and address problem later
40
+ else
41
+ false
42
+ end
43
+ end
44
+
45
+ def set_current_from_mark mark
46
+ self.current_id =
47
+ if mark.to_s =~ /@/
48
+ account = Auth[mark.downcase]
49
+ account && account.active? ? account.left_id : Card::AnonymousID
50
+ else
51
+ mark
52
+ end
53
+ end
54
+
55
+ def find_by_token token
56
+ Auth.as_bot do
57
+ Card.search(
58
+ right_id: Card::AccountID,
59
+ right_plus: [{ id: Card::TokenID }, { content: token.strip }]
60
+ ).first
61
+ end
62
+ end
63
+
29
64
  # Encrypts some data with the salt.
30
65
  def encrypt password, salt
31
66
  Digest::SHA1.hexdigest "#{salt}--#{password}--"
32
67
  end
33
68
 
34
- # find accounted by email
69
+ # find account by email
35
70
  def [] email
71
+ email = email.strip.downcase
36
72
  Auth.as_bot do
37
- Card.search(right_plus: [
38
- { id: Card::AccountID },
39
- { right_plus: [
40
- { id: Card::EmailID }, { content: email.strip.downcase }
41
- ] }
42
- ]).first
73
+ Card.search(
74
+ right_id: Card::AccountID,
75
+ right_plus: [{ id: Card::EmailID }, { content: email }]
76
+ ).first
43
77
  end
44
78
  end
45
79
 
@@ -78,6 +112,7 @@ class Card
78
112
 
79
113
  def current_id= card_id
80
114
  @@current = @@as_id = @@as_card = nil
115
+ card_id = card_id.to_i if card_id.present?
81
116
  @@current_id = card_id
82
117
  end
83
118
 
@@ -90,15 +125,21 @@ class Card
90
125
  end
91
126
 
92
127
  def as given_user
93
- tmp_id, tmp_card = @@as_id, @@as_card
128
+ tmp_id = @@as_id
129
+ tmp_card = @@as_card
130
+
131
+ @@as_id = get_user_id(given_user)
132
+ @@as_card = nil
94
133
  # we could go ahead and set as_card if given a card...
95
- @@as_id, @@as_card = get_user_id(given_user), nil
96
134
 
97
135
  @@current_id = @@as_id if @@current_id.nil?
98
136
 
99
137
  return unless block_given?
100
138
  value = yield
101
- @@as_id, @@as_card = tmp_id, tmp_card
139
+
140
+ @@as_id = tmp_id
141
+ @@as_card = tmp_card
142
+
102
143
  value
103
144
  end
104
145
 
@@ -146,8 +187,12 @@ class Card
146
187
  end
147
188
 
148
189
  def always_ok?
149
- # warn Rails.logger.warn("aok? #{as_id}, #{as_id&&Card[as_id].id}")
150
- return false unless (usr_id = as_id)
190
+ usr_id = as_id
191
+ return false if !usr_id
192
+ always_ok_usr_id? usr_id
193
+ end
194
+
195
+ def always_ok_usr_id? usr_id
151
196
  return true if usr_id == Card::WagnBotID # cannot disable
152
197
 
153
198
  always = Card.cache.read('ALWAYS') || {}
@@ -163,6 +208,7 @@ class Card
163
208
  # warn Rails.logger.warn("aok? #{usr_id}, #{always[usr_id]}")
164
209
  always[usr_id]
165
210
  end
211
+
166
212
  # PERMISSIONS
167
213
 
168
214
  def createable_types
@@ -54,11 +54,13 @@ class Card
54
54
  end
55
55
 
56
56
  def generate_cache_id
57
- ((Time.now.to_f * 100).to_i).to_s + ('a'..'z').to_a[rand(26)] + ('a'..'z').to_a[rand(26)]
57
+ ((Time.now.to_f * 100).to_i).to_s +
58
+ ('a'..'z').to_a[rand(26)] +
59
+ ('a'..'z').to_a[rand(26)]
58
60
  end
59
61
 
60
62
  def reset_global
61
- cache_by_class.each do |klass, cache|
63
+ cache_by_class.each do |_klass, cache|
62
64
  cache.reset hard=true
63
65
  end
64
66
  Card::Codename.reset_cache
@@ -67,9 +69,11 @@ class Card
67
69
 
68
70
  def reset_local
69
71
  cache_by_class.each do |cc, cache|
70
- if Card::Cache===cache
72
+ if Card::Cache === cache
71
73
  cache.reset_local
72
- else warn "reset class #{cc}, #{cache.class} #{caller[0..8]*"\n"} ???" end
74
+ else
75
+ warn "reset class #{cc}, #{cache.class} #{caller[0..8] * "\n"} ???"
76
+ end
73
77
  end
74
78
  end
75
79
 
@@ -91,20 +95,16 @@ class Card
91
95
  private
92
96
 
93
97
  def prepopulate
94
- if @@prepopulating
95
- @@rule_cache ||= Card.rule_cache
96
- @@read_rule_cache ||= Card.read_rule_cache
97
- @@user_ids_cache ||= Card.user_ids_cache
98
- @@rule_keys_cache ||= Card.rule_keys_cache
99
- Card.cache.write_local 'RULES', @@rule_cache
100
- Card.cache.write_local 'READRULES', @@read_rule_cache
101
- Card.cache.write_local 'USER_IDS', @@user_ids_cache
102
- Card.cache.write_local 'RULE_KEYS', @@rule_keys_cache
103
- end
98
+ return unless @@prepopulating
99
+ @@rule_cache ||= Card.rule_cache
100
+ @@user_ids_cache ||= Card.user_ids_cache
101
+ @@read_rule_cache ||= Card.read_rule_cache
102
+ @@rule_keys_cache ||= Card.rule_keys_cache
103
+ Card.cache.write_local 'RULES', @@rule_cache
104
+ Card.cache.write_local 'READRULES', @@read_rule_cache
105
+ Card.cache.write_local 'USER_IDS', @@user_ids_cache
106
+ Card.cache.write_local 'RULE_KEYS', @@rule_keys_cache
104
107
  end
105
-
106
-
107
-
108
108
  end
109
109
 
110
110
  attr_reader :prefix, :store, :klass
@@ -179,7 +179,7 @@ class Card
179
179
 
180
180
  def delete key
181
181
  @store.delete(@prefix + key) if @store
182
- @local.delete key
182
+ delete_local key
183
183
  end
184
184
 
185
185
  def delete_local key
@@ -66,29 +66,29 @@ class Card
66
66
  #include Card::Location
67
67
 
68
68
  def location_history
69
- #warn "sess #{session.class}, #{session.object_id}"
70
69
  session[:history] ||= [Card::Location.card_path('')]
71
- if session[:history]
72
- session[:history].shift if session[:history].size > 5
73
- session[:history]
74
- end
70
+ session[:history].shift if session[:history].size > 5
71
+ session[:history]
75
72
  end
76
73
 
77
74
  def save_location card
78
- return if Env.ajax? || !Env.html? || !card.known? || (card.codename == 'signin')
75
+ return if Env.ajax? || !Env.html? || !card.known? ||
76
+ (card.codename == 'signin')
79
77
  discard_locations_for card
80
- session[:previous_location] = Card::Location.card_path card.cardname.url_key
78
+ session[:previous_location] =
79
+ Card::Location.card_path card.cardname.url_key
81
80
  location_history.push previous_location
82
81
  end
83
82
 
84
83
  def previous_location
85
- session[:previous_location] ||= location_history.last if location_history
84
+ return unless location_history
85
+ session[:previous_location] ||= location_history.last
86
86
  end
87
87
 
88
- def discard_locations_for(card)
88
+ def discard_locations_for card
89
89
  # quoting necessary because cards have things like "+*" in the names..
90
90
  session[:history] = location_history.reject do |loc|
91
- if url_key = url_key_for_location(loc)
91
+ if (url_key = url_key_for_location(loc))
92
92
  url_key.to_name.key == card.key
93
93
  end
94
94
  end.compact
@@ -443,8 +443,9 @@ class Card
443
443
  end
444
444
 
445
445
  def nest nested_card, opts={}
446
- #ActiveSupport::Notifications.instrument('card', message: "nest: #{nested_card.name}, #{opts}") do
447
- opts.delete_if { |k,v| v.nil? }
446
+ # ActiveSupport::Notifications.instrument('card', message:
447
+ # "nest: #{nested_card.name}, #{opts}") do
448
+ opts.delete_if { |_k, v| v.nil? }
448
449
  opts.reverse_merge! inclusion_defaults(nested_card)
449
450
 
450
451
  sub = nil
@@ -455,37 +456,48 @@ class Card
455
456
  sub.inclusion_opts = opts[:items] ? opts[:items].clone : {}
456
457
  end
457
458
 
458
-
459
459
  view = canonicalize_view opts.delete :view
460
460
  opts[:home_view] = [:closed, :edit].member?(view) ? :open : view
461
461
  # FIXME: special views should be represented in view definitions
462
462
 
463
- view = case @mode
464
- when :edit
465
- not_ready_for_form = @@perms[view]==:none || nested_card.structure || nested_card.key.blank? # eg {{_self|type}} on new cards
466
- not_ready_for_form ? :blank : :edit_in_form
467
- when :template
468
- :template_rule
469
- when :closed
470
- case
471
- when @@closed_views[view] == true || @@error_codes[view] ; view
472
- when specified_view = @@closed_views[view] ; specified_view
473
- when !nested_card.known? ; :closed_missing
474
- else ; :closed_content
463
+ view =
464
+ case @mode
465
+ when :edit then view_in_edit_mode(view, nested_card)
466
+ when :template then :template_rule
467
+ when :closed then view_in_closed_mode(view, nested_card)
468
+ else view
475
469
  end
476
- else
477
- view
478
- end
479
470
 
480
471
  sub.optional_render view, opts
481
- #end
472
+ # end
473
+ end
474
+
475
+ def view_in_edit_mode homeview, nested_card
476
+ not_in_form =
477
+ @@perms[homeview] == :none || # view configured not to keep in form
478
+ nested_card.structure || # not yet nesting structures
479
+ nested_card.key.blank? # eg {{_self|type}} on new cards
480
+
481
+ not_in_form ? :blank : :edit_in_form
482
+ end
483
+
484
+ def view_in_closed_mode homeview, nested_card
485
+ approved_view = @@closed_views[homeview]
486
+ case
487
+ when approved_view == true then homeview
488
+ when @@error_codes[homeview] then homeview
489
+ when approved_view then approved_view
490
+ when !nested_card.known? then :closed_missing
491
+ else :closed_content
492
+ end
482
493
  end
483
494
 
484
495
  def get_inclusion_content cardname
485
- content = params[cardname.to_s.gsub(/\+/,'_')]
496
+ content = params[cardname.to_s.tr('+', '_')]
486
497
 
487
- # CLEANME This is a hack to get it so plus cards re-populate on failed signups
488
- if p = params['subcards'] and card_params = p[cardname.to_s]
498
+ # CLEANME This is a hack so plus cards re-populate on failed signups
499
+ p = params['subcards']
500
+ if p && card_params = p[cardname.to_s]
489
501
  content = card_params['content']
490
502
  end
491
503
  content if content.present? # why is this necessary? - efm
@@ -510,26 +522,26 @@ class Card
510
522
  :name
511
523
  end
512
524
 
513
-
514
525
  #
515
526
  # ------------ LINKS ---------------
516
527
  #
517
528
 
518
529
  def add_class options, klass
519
- options[:class] = [ options[:class], klass ].flatten.compact * ' '
530
+ options[:class] = [options[:class], klass].flatten.compact * ' '
520
531
  end
521
532
 
522
-
523
533
  def unique_id
524
534
  "#{card.key}-#{Time.now.to_i}-#{rand(3)}"
525
535
  end
526
536
 
527
- def format_date date, include_time = true
528
- # Must use DateTime because Time doesn't support %e on at least some platforms
537
+ def format_date date, include_time=true
538
+ # using DateTime because Time doesn't support %e on some platforms
529
539
  if include_time
530
- DateTime.new(date.year, date.mon, date.day, date.hour, date.min, date.sec).strftime("%B %e, %Y %H:%M:%S")
540
+ DateTime.new(
541
+ date.year, date.mon, date.day, date.hour, date.min, date.sec
542
+ ).strftime('%B %e, %Y %H:%M:%S')
531
543
  else
532
- DateTime.new(date.year, date.mon, date.day).strftime("%B %e, %Y")
544
+ DateTime.new(date.year, date.mon, date.day).strftime('%B %e, %Y')
533
545
  end
534
546
  end
535
547
 
@@ -538,7 +550,6 @@ class Card
538
550
  @context_names += name.to_name.part_names
539
551
  @context_names.uniq!
540
552
  end
541
-
542
553
  end
543
554
  end
544
555
 
@@ -1,8 +1,7 @@
1
1
  class Card
2
-
3
2
  module Location
4
- #
5
- # page_path takes a Card::Name, adds the format and query string to url_key (site-absolute)
3
+ # page_path takes a Card::Name, adds the format and query string to
4
+ # url_key (site-absolute)
6
5
  # card_path makes a relative path site-absolute (if not already)
7
6
  # card_url makes it a full url (if not already)
8
7
 
@@ -34,5 +33,4 @@ class Card
34
33
 
35
34
  extend Location
36
35
  end
37
-
38
- end
36
+ end
@@ -98,11 +98,8 @@ class Card
98
98
 
99
99
  def rename old_name, new_name
100
100
  return unless @keys.include? old_name.to_name.key
101
-
102
101
  end
103
102
 
104
-
105
-
106
103
  def << value
107
104
  add value
108
105
  end
@@ -11,9 +11,6 @@ class Card
11
11
  case success_params
12
12
  when Hash
13
13
  apply(success_params)
14
- when /^REDIRECT:\s*(.+)/
15
- @redirect=true
16
- self.target = $1
17
14
  when nil ; self.name = '_self'
18
15
  else ; self.target = success_params
19
16
  end
@@ -59,14 +56,20 @@ class Card
59
56
 
60
57
  def target= value
61
58
  @id = @name = @card = nil
62
- @target =
63
- case value
64
- when '*previous', :previous ; :previous
65
- when /^(http|\/)/ ; value
66
- when /^TEXT:\s*(.+)/ ; $1
67
- when '' ; ''
68
- else ; self.mark = value
69
- end
59
+ @target = process_target value
60
+ end
61
+
62
+ def process_target value
63
+ case value
64
+ when '' then ''
65
+ when '*previous', :previous then :previous
66
+ when /^(http|\/)/ then value
67
+ when /^TEXT:\s*(.+)/ then $1
68
+ when /^REDIRECT:\s*(.+)/
69
+ @redirect = true
70
+ process_target $1
71
+ else self.mark = value
72
+ end
70
73
  end
71
74
 
72
75
  def apply args