Class: Certification

Inherits:
ApplicationRecord show all
Includes:
Models::Auditable, Models::LiquidMethods
Defined in:
app/models/certification.rb

Overview

== Schema Information

Table name: certifications
Database name: primary

id :bigint not null, primary key
attachment_name :string
attachment_uid :string
certified_by :integer
certified_on :datetime
expiration_reminder_10_days_sent :boolean default(FALSE), not null
expiration_reminder_10_days_sent_on :datetime
expiration_reminder_30_days_sent :boolean default(FALSE), not null
expiration_reminder_30_days_sent_on :datetime
expired_reminder_sent :boolean default(FALSE), not null
expired_reminder_sent_on :datetime
expires_at :datetime
reference :string
state :string
title :string
welcome_meeting :boolean default(FALSE), not null
welcome_meeting_date :datetime
workshop_attended :boolean
workshop_attended_date :datetime
created_at :datetime not null
updated_at :datetime not null
course_enrollment_id :integer
party_id :integer

Indexes

idx_party_id (party_id)

Constant Summary

Constants included from Models::Auditable

Models::Auditable::ALWAYS_IGNORED

Constants included from Schedulable

Schedulable::SIMPLE_FORM_OPTIONS

Belongs to collapse

Methods included from Models::Auditable

#creator, #updater

Has one collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Models::Auditable

#all_skipped_columns, #audit_reference_data, #should_not_save_version, #stamp_record

Methods inherited from ApplicationRecord

ransackable_associations, ransackable_attributes, ransackable_scopes, ransortable_attributes, #to_relation

Methods included from Schedulable

config

Methods included from Models::AfterCommittable

#after_commit

Methods included from Models::EventPublishable

#publish_event

Class Method Details

.activeActiveRecord::Relation<Certification>

A relation of Certifications that are active. Active Record Scope

Returns:

See Also:



56
# File 'app/models/certification.rb', line 56

scope :active, -> { where(state: 'active') }

.expiredActiveRecord::Relation<Certification>

A relation of Certifications that are expired. Active Record Scope

Returns:

See Also:



57
# File 'app/models/certification.rb', line 57

scope :expired, -> { where(state: 'expired') }

.requestedActiveRecord::Relation<Certification>

A relation of Certifications that are requested. Active Record Scope

Returns:

See Also:



58
# File 'app/models/certification.rb', line 58

scope :requested, -> { where(state: 'requested') }

.titleObject



203
204
205
# File 'app/models/certification.rb', line 203

def self.title
  title || course_enrollment.course&.name
end

Instance Method Details

#agreementAgreement

Returns:

See Also:



52
# File 'app/models/certification.rb', line 52

has_one :agreement, as: :resource

#agreement_ok?Boolean

Returns:

  • (Boolean)


139
140
141
# File 'app/models/certification.rb', line 139

def agreement_ok?
  agreement.present? && agreement.signed?
end

#can_be_activated?Boolean

Returns:

  • (Boolean)


114
115
116
117
118
119
120
121
122
123
124
125
# File 'app/models/certification.rb', line 114

def can_be_activated?
  # There needs to be at least 1 liability insurance active at this moment
  liability = liability_ok?
  # An online welcome meeting needs to happen before being activated
  meeting = welcome_meeting_ok?
  # Pro needs to attend at least one workshop
  workshop = workshop_attended_ok?
  # The agreement needs to be signed and uploaded
  agreement = agreement_ok?

  liability && meeting && workshop && agreement
end


207
208
209
# File 'app/models/certification.rb', line 207

def certificate_link
  "#{WEB_URL}/my_account/certifications/#{id}"
end

#contactParty

NOTE: no inverse_of: here. contact is a same-FK alias of customer/party
(all three resolve party_id to the STI-typed Party). The base Party class has
no :certifications association — only the subclasses (Contact/Customer/Employee)
do — so inverse_of: :certifications raised "Could not find the inverse
association for contact (:certifications in Party)" whenever #contact was
touched (AppSignal #6034). The sibling :customer/:party work fine without it.

Returns:

See Also:



50
# File 'app/models/certification.rb', line 50

belongs_to :contact, class_name: 'Party', foreign_key: 'party_id', optional: true

#course_enrollmentCourseEnrollment



41
# File 'app/models/certification.rb', line 41

belongs_to :course_enrollment, optional: true

#create_agreementObject



155
156
157
158
159
160
161
# File 'app/models/certification.rb', line 155

def create_agreement
  agreement = build_agreement(sign_method: 'esignatures', template: 'installer_agreement')
  agreement.agreement_participants.new(
    party_id: party_id
  )
  agreement.send_to_esignatures if agreement.save
end

#create_welcome_meeting_activityObject



227
228
229
230
231
232
233
# File 'app/models/certification.rb', line 227

def create_welcome_meeting_activity
  Activity.create(lock_target_datetime: true,
                  activity_type_id: ActivityType.find_by(task_type: 'INSTALL_CERTIFICATION_PM')&.id,
                  party: party,
                  resource: self,
                  notes: "Welcome meeting for new certification request. Please arrange meeting.")
end

#create_workshop_activityObject



219
220
221
222
223
224
225
# File 'app/models/certification.rb', line 219

def create_workshop_activity
  Activity.create(lock_target_datetime: true,
                  activity_type_id: ActivityType.find_by(task_type: 'INSTALL_CERTIFICATION_PWS')&.id,
                  party: party,
                  resource: self,
                  notes: "New certification requires workshop to attend. Please schedule and verify this customer attends.")
end

#customerParty

Returns:

See Also:



43
# File 'app/models/certification.rb', line 43

belongs_to :customer, class_name: 'Party', foreign_key: 'party_id', optional: true

#liability_ok?Boolean

Returns:

  • (Boolean)


127
128
129
# File 'app/models/certification.rb', line 127

def liability_ok?
  party.customer.liability_insurances.active.any? && customer.liability_insurances.effective_on(Time.current).present?
end

#partyParty

Returns:

See Also:



42
# File 'app/models/certification.rb', line 42

belongs_to :party, optional: true

#possible_eventsObject



211
212
213
# File 'app/models/certification.rb', line 211

def possible_events
  state_transitions.map(&:event).sort
end

#possible_events_for_selectObject



215
216
217
# File 'app/models/certification.rb', line 215

def possible_events_for_select
  possible_events.map { |evt| [evt.to_s.titleize, evt] }
end

#send_admin_alertObject



199
200
201
# File 'app/models/certification.rb', line 199

def send_admin_alert
  TrainingMailer.new_certification_request(self).deliver_later!
end

#send_congratulations_emailObject



163
164
165
166
167
168
169
# File 'app/models/certification.rb', line 163

def send_congratulations_email
  customer = party
  CommunicationBuilder.new(resource: self,
                                  recipient_party: customer,
                                  use_best_email: true,
                                  template_system_code: 'NEW_INSTALLER').create
end

#send_expiration_reminderObject



189
190
191
192
193
194
195
196
197
# File 'app/models/certification.rb', line 189

def send_expiration_reminder
  TrainingMailer.certification_expired(self).deliver_later!
  customer = party
  CommunicationBuilder.new(resource: self,
                                  recipient_party: customer,
                                  use_best_email: true,
                                  template_system_code: 'CERT_EXPIRED').create
  update(expired_reminder_sent: true, expired_reminder_sent_on: Time.current)
end

#send_expiration_reminder_10Object



180
181
182
183
184
185
186
187
# File 'app/models/certification.rb', line 180

def send_expiration_reminder_10
  customer = party
  CommunicationBuilder.new(resource: self,
                                  recipient_party: customer,
                                  use_best_email: true,
                                  template_system_code: 'CERT_EXPIRES_10').create
  update(expiration_reminder_10_days_sent: true, expiration_reminder_10_days_sent_on: Time.current)
end

#send_expiration_reminder_30Object



171
172
173
174
175
176
177
178
# File 'app/models/certification.rb', line 171

def send_expiration_reminder_30
  customer = party
  CommunicationBuilder.new(resource: self,
                                  recipient_party: customer,
                                  use_best_email: true,
                                  template_system_code: 'CERT_EXPIRES_30').create
  update(expiration_reminder_30_days_sent: true, expiration_reminder_30_days_sent_on: Time.current)
end

#set_partyObject



151
152
153
# File 'app/models/certification.rb', line 151

def set_party
  self.party_id = course_enrollment.party.id if course_enrollment.party.present? && party_id.nil?
end

#set_reference_numberObject



147
148
149
# File 'app/models/certification.rb', line 147

def set_reference_number
  update(reference: "CER#{id.to_s.rjust(4, '0')}")
end

#set_titleObject



143
144
145
# File 'app/models/certification.rb', line 143

def set_title
  self.title = course_enrollment&.course&.name if title.blank?
end

#welcome_meeting_ok?Boolean

Returns:

  • (Boolean)


131
132
133
# File 'app/models/certification.rb', line 131

def welcome_meeting_ok?
  welcome_meeting.to_b
end

#workshop_attended_ok?Boolean

Returns:

  • (Boolean)


135
136
137
# File 'app/models/certification.rb', line 135

def workshop_attended_ok?
  workshop_attended.to_b
end