effective_memberships 0.17.7 → 0.17.9
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.
- checksums.yaml +4 -4
- data/app/datatables/admin/effective_memberships_datatable.rb +7 -1
- data/app/models/concerns/effective_memberships_applicant.rb +18 -2
- data/app/models/concerns/effective_memberships_applicant_review.rb +10 -0
- data/app/models/concerns/effective_memberships_category.rb +4 -0
- data/app/models/concerns/effective_memberships_owner.rb +46 -0
- data/app/models/concerns/effective_memberships_status.rb +2 -3
- data/app/models/effective/applicant_reference.rb +15 -0
- data/app/models/effective/membership.rb +19 -0
- data/app/models/effective/membership_history.rb +14 -0
- data/app/views/admin/memberships/_form_membership.html.haml +2 -0
- data/app/views/effective/memberships/_dashboard.html.haml +4 -1
- data/app/views/effective/memberships/_reclassification.html.haml +14 -0
- data/app/views/effective/memberships/_reinstatement.html.haml +14 -0
- data/lib/effective_memberships/version.rb +1 -1
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 7a7ab7d95194d5d7c49af9f4d8297b4a9f927f9d4a2d97ea2f18ead660488685
|
4
|
+
data.tar.gz: 7412d96bc6f4b1c7329a3fa2b4998e0045d921f1deec09886f024f42b868afc7
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 6aeaa23fda513f0b707252be4009fa6b25c19a8ee9f7ead8761a15893fa5b56a2b1ddba20da408e42f5d8c7759dc1b53c9faba19b20eecac28b5dfdf863c8703
|
7
|
+
data.tar.gz: d2abd9350b5b98b43db54214b9cdf4a8fdc40858a66a4ea8f0ad301870326d16892287ad5ae1ac4a8dda70db2545e0d4ed12092e2bf265b3ae249137323bc311
|
@@ -64,7 +64,13 @@ module Admin
|
|
64
64
|
membership.owner.try(:addresses).try(:first).try(:postal_code)
|
65
65
|
end
|
66
66
|
|
67
|
-
actions_col
|
67
|
+
actions_col do |membership|
|
68
|
+
if membership.owner_type.include?('Organization')
|
69
|
+
dropdown_link_to 'Show', "/admin/organizations/#{membership.owner.to_param}/edit#tab-membership", 'data-turbolinks': false
|
70
|
+
elsif membership.owner_type.include?('User')
|
71
|
+
dropdown_link_to 'Show', "/admin/users/#{membership.owner.to_param}/edit#tab-membership", 'data-turbolinks': false
|
72
|
+
end
|
73
|
+
end
|
68
74
|
end
|
69
75
|
|
70
76
|
collection do
|
@@ -192,7 +192,7 @@ module EffectiveMembershipsApplicant
|
|
192
192
|
|
193
193
|
# effective_reports
|
194
194
|
def reportable_scopes
|
195
|
-
{ draft: nil, submitted: nil, in_progress: nil, done: nil }
|
195
|
+
{ draft: nil, submitted: nil, missing_info: nil, completed: nil, reviewed: nil, declined: nil, approved: nil, in_progress: nil, done: nil }
|
196
196
|
end
|
197
197
|
|
198
198
|
scope :deep, -> { includes(:user, :organization, :category, :from_category, :from_status, :orders) }
|
@@ -202,7 +202,6 @@ module EffectiveMembershipsApplicant
|
|
202
202
|
scope :done, -> { where(status: [:approved, :declined]) }
|
203
203
|
|
204
204
|
scope :not_draft, -> { where.not(status: :draft) }
|
205
|
-
|
206
205
|
scope :reviewable, -> { where.not(status: [:draft, :submitted, :declined, :approved]) }
|
207
206
|
|
208
207
|
scope :for, -> (user) {
|
@@ -251,6 +250,23 @@ module EffectiveMembershipsApplicant
|
|
251
250
|
validates :category, presence: true
|
252
251
|
end
|
253
252
|
|
253
|
+
# Select Step - Check for expired reclassification or reinstatement dates
|
254
|
+
validate(if: -> { current_step == :select && owner.present? && applicant_type.present? && category.present? }) do
|
255
|
+
# Dates
|
256
|
+
today = (created_at || Time.zone.now).beginning_of_day
|
257
|
+
|
258
|
+
reclassification_expires_on = owner.reclassification_expires_on(from: from_category, to: category)
|
259
|
+
reinstatement_expires_on = owner.reinstatement_expires_on(from: from_status)
|
260
|
+
|
261
|
+
if reclassification? && reclassification_expires_on.present? && reclassification_expires_on <= today
|
262
|
+
errors.add(:base, "Your ability to apply for reclassification expired on #{reclassification_expires_on.strftime('%F')}. Please contact us for assistance.")
|
263
|
+
end
|
264
|
+
|
265
|
+
if reinstatement? && reinstatement_expires_on.present? && reinstatement_expires_on <= today
|
266
|
+
errors.add(:base, "Your ability to apply for reinstatement expired on #{reinstatement_expires_on.strftime('%F')}. Please contact us for assistance.")
|
267
|
+
end
|
268
|
+
end
|
269
|
+
|
254
270
|
# They can checkout with outstanding fees
|
255
271
|
# validate(if: -> { current_step == :select && owner.present? }) do
|
256
272
|
# self.errors.add(:base, 'may not have outstanding fees') if owner.outstanding_fee_payment_fees.present?
|
@@ -29,6 +29,7 @@ module EffectiveMembershipsApplicantReview
|
|
29
29
|
|
30
30
|
included do
|
31
31
|
log_changes(to: :applicant) if respond_to?(:log_changes)
|
32
|
+
acts_as_reportable if respond_to?(:acts_as_reportable)
|
32
33
|
|
33
34
|
acts_as_tokened
|
34
35
|
|
@@ -59,6 +60,15 @@ module EffectiveMembershipsApplicantReview
|
|
59
60
|
timestamps
|
60
61
|
end
|
61
62
|
|
63
|
+
# effective_reports
|
64
|
+
def reportable_scopes
|
65
|
+
{ in_progress: nil, done: nil }
|
66
|
+
end
|
67
|
+
|
68
|
+
def reportable_email
|
69
|
+
reviewer.try(:email)
|
70
|
+
end
|
71
|
+
|
62
72
|
scope :deep, -> { includes(:reviewer, applicant: [:user, :applicant_reviews]) }
|
63
73
|
|
64
74
|
scope :for, -> (user) {
|
@@ -137,6 +137,44 @@ module EffectiveMembershipsOwner
|
|
137
137
|
removed_membership_history.start_on if membership_removed?
|
138
138
|
end
|
139
139
|
|
140
|
+
# Checked by the applicant on the select step
|
141
|
+
def reclassification_expires_on(from: nil, to: nil)
|
142
|
+
return unless membership.present?
|
143
|
+
|
144
|
+
# User/owner might respond to this
|
145
|
+
date = try(:admin_reclassification_expires_on)
|
146
|
+
return date if date.present?
|
147
|
+
|
148
|
+
# When we last reclassified to our current category
|
149
|
+
history = last_membership_history(category: membership.membership_categories.first)
|
150
|
+
reclassified_on = (history&.start_on || membership.registration_on || membership.joined_on)
|
151
|
+
|
152
|
+
# Otherwise consider the membership categories
|
153
|
+
expires_on = membership.categories.select { |category| category.reclassification_expires_in.present? }.map do |category|
|
154
|
+
reclassified_on + category.reclassification_expires_in
|
155
|
+
end.min
|
156
|
+
|
157
|
+
expires_on
|
158
|
+
end
|
159
|
+
|
160
|
+
def reinstatement_expires_on(from: nil)
|
161
|
+
return unless membership_removed?
|
162
|
+
|
163
|
+
# User/owner might respond to this
|
164
|
+
date = try(:admin_reinstatement_expires_on)
|
165
|
+
return date if date.present?
|
166
|
+
|
167
|
+
# When we were removed
|
168
|
+
removed_on = removed_membership_history.start_on
|
169
|
+
|
170
|
+
# Consider any membership statuses that have reinstatement expires in
|
171
|
+
expires_on = removed_membership_history.membership_statuses.select { |status| status.reinstatement_expires_in.present? }.map do |status|
|
172
|
+
removed_on + status.reinstatement_expires_in
|
173
|
+
end.min
|
174
|
+
|
175
|
+
expires_on
|
176
|
+
end
|
177
|
+
|
140
178
|
# The membership history that is removed. Has exit statuses that may affect reinstatement fees.
|
141
179
|
def removed_membership_history
|
142
180
|
membership_histories.reverse.find { |history| history.removed? } if membership_removed?
|
@@ -444,6 +482,14 @@ module EffectiveMembershipsOwner
|
|
444
482
|
membership_histories.find { |history| (history.start_on..history.end_on).cover?(date) } # Ruby 2.6 supports endless ranges
|
445
483
|
end
|
446
484
|
|
485
|
+
def first_membership_history(category: nil)
|
486
|
+
membership_histories.find { |history| category.blank? || history.membership_category_ids.include?(category.id) }
|
487
|
+
end
|
488
|
+
|
489
|
+
def last_membership_history(category: nil)
|
490
|
+
membership_histories.reverse.find { |history| category.blank? || history.membership_category_ids.include?(category.id) }
|
491
|
+
end
|
492
|
+
|
447
493
|
# Point out busted data
|
448
494
|
def membership_history_errors
|
449
495
|
return unless membership.present?
|
@@ -11,6 +11,7 @@ module Effective
|
|
11
11
|
)
|
12
12
|
|
13
13
|
log_changes(to: :applicant) if respond_to?(:log_changes)
|
14
|
+
acts_as_reportable if respond_to?(:acts_as_reportable)
|
14
15
|
|
15
16
|
belongs_to :applicant, polymorphic: true, optional: true
|
16
17
|
|
@@ -52,6 +53,20 @@ module Effective
|
|
52
53
|
timestamps
|
53
54
|
end
|
54
55
|
|
56
|
+
# effective_reports
|
57
|
+
def reportable_scopes
|
58
|
+
{ in_progress: nil, done: nil, expired: nil }
|
59
|
+
end
|
60
|
+
|
61
|
+
scope :in_progress, -> { with_submitted_applicants.where(status: :submitted) }
|
62
|
+
scope :done, -> { where(status: :completed) }
|
63
|
+
|
64
|
+
scope :expired, -> { where(status: :submitted).where.not(with_submitted_applicants) }
|
65
|
+
|
66
|
+
scope :with_submitted_applicants, -> {
|
67
|
+
where(applicant_id: EffectiveMemberships.Applicant.submitted)
|
68
|
+
}
|
69
|
+
|
55
70
|
scope :deep, -> { all }
|
56
71
|
|
57
72
|
# All step validations
|
@@ -11,6 +11,7 @@ module Effective
|
|
11
11
|
has_many :membership_statuses, -> { order(:id) }, inverse_of: :membership, dependent: :delete_all
|
12
12
|
accepts_nested_attributes_for :membership_statuses
|
13
13
|
|
14
|
+
acts_as_reportable if respond_to?(:acts_as_reportable)
|
14
15
|
log_changes(to: :owner) if respond_to?(:log_changes)
|
15
16
|
|
16
17
|
effective_resource do
|
@@ -35,7 +36,23 @@ module Effective
|
|
35
36
|
scope :deep, -> { includes(:owner, membership_categories: :category, membership_statuses: :status) }
|
36
37
|
scope :sorted, -> { order('lower(owner_name)') }
|
37
38
|
|
39
|
+
# effective_reports
|
40
|
+
def reportable_scopes
|
41
|
+
{
|
42
|
+
with_category: :string,
|
43
|
+
with_status: :string,
|
44
|
+
joined_before: :date,
|
45
|
+
joined_after: :date,
|
46
|
+
with_paid_fees_through: :date,
|
47
|
+
with_unpaid_fees_through: :date,
|
48
|
+
in_good_standing: nil,
|
49
|
+
not_in_good_standing: nil
|
50
|
+
}
|
51
|
+
end
|
52
|
+
|
38
53
|
scope :with_status, -> (statuses) {
|
54
|
+
statuses = Resource.new(EffectiveMemberships.Status).search_any(statuses) if statuses.kind_of?(String)
|
55
|
+
|
39
56
|
raise('expected an EffectiveMemberships.Status') unless statuses.class.respond_to?(:effective_memberships_status?) || Array(statuses).all? { |status| status.kind_of?(EffectiveMemberships.Status) }
|
40
57
|
where(id: MembershipStatus.where(status_id: statuses).select(:membership_id))
|
41
58
|
}
|
@@ -46,6 +63,8 @@ module Effective
|
|
46
63
|
}
|
47
64
|
|
48
65
|
scope :with_category, -> (categories) {
|
66
|
+
categories = Resource.new(EffectiveMemberships.Category).search_any(categories) if categories.kind_of?(String)
|
67
|
+
|
49
68
|
raise('expected an EffectiveMemberships.Category') unless categories.class.respond_to?(:effective_memberships_category?) || Array(categories).all? { |cat| cat.kind_of?(EffectiveMemberships.Category) }
|
50
69
|
where(id: MembershipCategory.where(category_id: categories).select(:membership_id))
|
51
70
|
}
|
@@ -2,6 +2,8 @@ module Effective
|
|
2
2
|
class MembershipHistory < ActiveRecord::Base
|
3
3
|
belongs_to :owner, polymorphic: true
|
4
4
|
|
5
|
+
acts_as_reportable if respond_to?(:acts_as_reportable)
|
6
|
+
|
5
7
|
effective_resource do
|
6
8
|
start_on :date
|
7
9
|
end_on :date
|
@@ -13,20 +15,32 @@ module Effective
|
|
13
15
|
categories :text
|
14
16
|
category_ids :text
|
15
17
|
|
18
|
+
statuses :text
|
19
|
+
status_ids :text
|
20
|
+
|
16
21
|
notes :text
|
17
22
|
|
18
23
|
timestamps
|
19
24
|
end
|
20
25
|
|
26
|
+
# TODO: Rename categories to be category_toses
|
27
|
+
# And membreship_categories below should be called categories
|
28
|
+
|
21
29
|
serialize :categories, Array
|
22
30
|
serialize :category_ids, Array
|
23
31
|
|
24
32
|
serialize :statuses, Array
|
25
33
|
serialize :status_ids, Array
|
26
34
|
|
35
|
+
# effective_reports
|
36
|
+
def reportable_scopes
|
37
|
+
{ removed: nil, not_removed: nil }
|
38
|
+
end
|
39
|
+
|
27
40
|
scope :deep, -> { includes(:owner) }
|
28
41
|
scope :sorted, -> { order(:start_on).order(:id) }
|
29
42
|
|
43
|
+
scope :not_removed, -> { where(removed: false) }
|
30
44
|
scope :removed, -> { where(removed: true) }
|
31
45
|
|
32
46
|
validates :owner, presence: true
|
@@ -9,6 +9,8 @@
|
|
9
9
|
|
10
10
|
= f.static_field :current_action, label: 'Current Membership' do
|
11
11
|
= membership.to_s
|
12
|
+
= render('effective/memberships/reclassification', user: membership.owner)
|
13
|
+
= render('effective/memberships/reinstatement', user: membership.owner)
|
12
14
|
|
13
15
|
= f.check_box :current_action, label: 'Yes, update membership information'
|
14
16
|
|
@@ -33,11 +33,14 @@
|
|
33
33
|
- if membership.not_in_good_standing?
|
34
34
|
%p Your membership is Not In Good Standing because of unpurchased fees or dues. Please purchase these dues or contact us.
|
35
35
|
|
36
|
+
- if membership.present?
|
37
|
+
= render('effective/memberships/reclassification', user: current_user)
|
38
|
+
|
36
39
|
- if current_user.membership_removed?
|
37
40
|
%p Your membership was removed on #{current_user.membership_removed_on.strftime('%F')}.
|
38
41
|
|
39
42
|
- if current_user.reinstatement_membership_history.present?
|
40
|
-
|
43
|
+
= render('effective/memberships/reinstatement', user: current_user)
|
41
44
|
|
42
45
|
- if membership_organizations.present?
|
43
46
|
%p You are a representative for #{pluralize(membership_organizations.length, 'member organization')}.
|
@@ -0,0 +1,14 @@
|
|
1
|
+
- if user.membership.present?
|
2
|
+
- now = Time.zone.now.beginning_of_day
|
3
|
+
- applicants = user.applicants.select { |applicant| applicant.in_progress? }
|
4
|
+
|
5
|
+
- if applicants.blank?
|
6
|
+
- expires_on = user.reclassification_expires_on
|
7
|
+
- category = user.membership.categories.to_sentence
|
8
|
+
|
9
|
+
- if expires_on.blank?
|
10
|
+
- # Nothing to do
|
11
|
+
- elsif now < expires_on
|
12
|
+
%p You have until #{expires_on.strftime('%F')}, #{distance_of_time_in_words(now, expires_on)} from now, to Apply for Reclassification from #{category}.
|
13
|
+
- else
|
14
|
+
%p Your ability to Apply for Reclassification from #{category} expired on #{expires_on.strftime('%F')}.
|
@@ -0,0 +1,14 @@
|
|
1
|
+
- if user.reinstatement_membership_history.present?
|
2
|
+
- now = Time.zone.now.beginning_of_day
|
3
|
+
- applicants = user.applicants.select { |applicant| applicant.in_progress? }
|
4
|
+
|
5
|
+
- if applicants.blank?
|
6
|
+
- category = user.reinstatement_membership_category
|
7
|
+
- expires_on = user.reinstatement_expires_on
|
8
|
+
|
9
|
+
- if expires_on.blank?
|
10
|
+
- # Nothing to do
|
11
|
+
- elsif now < expires_on
|
12
|
+
%p You have until #{expires_on.strftime('%F')}, #{distance_of_time_in_words(now, expires_on)} from now, to Apply for Reinstatement to #{category}.
|
13
|
+
- else
|
14
|
+
%p Your ability to Apply for Reinstatement to #{category} expired on #{expires_on.strftime('%F')}.
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: effective_memberships
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.17.
|
4
|
+
version: 0.17.9
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Code and Effect
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-05-
|
11
|
+
date: 2023-05-25 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -525,6 +525,8 @@ files:
|
|
525
525
|
- app/views/effective/membership_directory/show.html.haml
|
526
526
|
- app/views/effective/memberships/_dashboard.html.haml
|
527
527
|
- app/views/effective/memberships/_membership.html.haml
|
528
|
+
- app/views/effective/memberships/_reclassification.html.haml
|
529
|
+
- app/views/effective/memberships/_reinstatement.html.haml
|
528
530
|
- app/views/effective/memberships_mailer/applicant_approved.liquid
|
529
531
|
- app/views/effective/memberships_mailer/applicant_completed.liquid
|
530
532
|
- app/views/effective/memberships_mailer/applicant_declined.liquid
|