Class: RailsOnboarding::MilestoneService
- Inherits:
-
Object
- Object
- RailsOnboarding::MilestoneService
- Defined in:
- app/services/rails_onboarding/milestone_service.rb
Class Method Summary collapse
- .check_and_award_milestones(user, trigger, conditions = {}) ⇒ Object
- .check_early_adopter_milestone(user) ⇒ Object
- .check_onboarding_completion_milestones(user) ⇒ Object
- .check_onboarding_step_milestones(user, step_name) ⇒ Object
-
.claim_if_eligible(user, milestone_key) ⇒ Hash?
Award a milestone requested by the client (e.g. the milestones API), but only if the user genuinely qualifies for it right now.
-
.custom_conditions_met?(user, conditions) ⇒ Boolean
Custom-trigger milestones can carry arbitrary host-defined conditions, so only the ones we know how to verify from the user's record are honored; everything else (including an empty condition set) is treated as unearned.
- .milestone_conditions_met?(user, milestone, trigger_conditions) ⇒ Boolean
-
.user_eligible_for?(user, milestone) ⇒ Boolean
Whether
userhas actually met the trigger a milestone is awarded for, checked against their real record - not against caller-supplied values.
Class Method Details
.check_and_award_milestones(user, trigger, conditions = {}) ⇒ Object
3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 3 def self.check_and_award_milestones(user, trigger, conditions = {}) return [] unless RailsOnboarding.configuration.enable_milestones return [] unless user eligible_milestones = RailsOnboarding.configuration.milestones_for_trigger(trigger, conditions) awarded_milestones = [] eligible_milestones.each do |milestone| next if user.milestone_achieved?(milestone[:key]) if milestone_conditions_met?(user, milestone, conditions) achieved_milestone = user.achieve_milestone!(milestone[:key]) awarded_milestones << achieved_milestone if achieved_milestone end end awarded_milestones end |
.check_early_adopter_milestone(user) ⇒ Object
30 31 32 33 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 30 def self.check_early_adopter_milestone(user) return [] unless user.created_at > 1.hour.ago check_and_award_milestones(user, :custom, { early_adopter: true }) end |
.check_onboarding_completion_milestones(user) ⇒ Object
26 27 28 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 26 def self.check_onboarding_completion_milestones(user) check_and_award_milestones(user, :onboarding_completed) end |
.check_onboarding_step_milestones(user, step_name) ⇒ Object
22 23 24 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 22 def self.check_onboarding_step_milestones(user, step_name) check_and_award_milestones(user, :onboarding_step_completed, { step: step_name.to_sym }) end |
.claim_if_eligible(user, milestone_key) ⇒ Hash?
Award a milestone requested by the client (e.g. the milestones API), but only if the user genuinely qualifies for it right now. Milestones are normally granted by the server-side event helpers above; this exists for clients that want to claim one explicitly, and it re-derives eligibility from the user's actual state so a request can't grant an unearned award.
43 44 45 46 47 48 49 50 51 52 53 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 43 def self.claim_if_eligible(user, milestone_key) return nil unless RailsOnboarding.configuration.enable_milestones return nil unless user return nil if user.milestone_achieved?(milestone_key) milestone = RailsOnboarding.configuration.milestone_by_key(milestone_key) return nil unless milestone return nil unless user_eligible_for?(user, milestone) user.achieve_milestone!(milestone[:key]) end |
.custom_conditions_met?(user, conditions) ⇒ Boolean
Custom-trigger milestones can carry arbitrary host-defined conditions, so only the ones we know how to verify from the user's record are honored; everything else (including an empty condition set) is treated as unearned.
77 78 79 80 81 82 83 84 85 86 87 88 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 77 def self.custom_conditions_met?(user, conditions) return false if conditions.blank? conditions.all? do |key, value| case key.to_sym when :early_adopter value == true && user.created_at.present? && user.created_at > 1.hour.ago else false end end end |
.milestone_conditions_met?(user, milestone, trigger_conditions) ⇒ Boolean
90 91 92 93 94 95 96 97 98 99 100 101 102 103 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 90 def self.milestone_conditions_met?(user, milestone, trigger_conditions) return true unless milestone[:conditions] milestone[:conditions].all? do |key, value| case key when :step trigger_conditions[:step] == value.to_sym when :early_adopter user.created_at > 1.hour.ago else trigger_conditions[key] == value end end end |
.user_eligible_for?(user, milestone) ⇒ Boolean
Whether user has actually met the trigger a milestone is awarded for,
checked against their real record - not against caller-supplied values.
Any trigger/condition we can't confirm server-side is denied.
60 61 62 63 64 65 66 67 68 69 70 71 72 |
# File 'app/services/rails_onboarding/milestone_service.rb', line 60 def self.user_eligible_for?(user, milestone) case milestone[:trigger] when :onboarding_step_completed step = milestone.dig(:conditions, :step) step.present? && user.step_completed?(step) when :onboarding_completed user.onboarding_completed? when :custom custom_conditions_met?(user, milestone[:conditions]) else false end end |