effective_cpd 1.1.3 → 1.2.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 00e8ed14d47f2bb89d1a33e12c76bf8e99b0470e65f7abcd282f23e0ec8b3a96
4
- data.tar.gz: 835ab26687db053debee149640fe8b06d6e05ce518bc4601cd5e5e8a7d4e0bec
3
+ metadata.gz: 13796b4516c32b7fd046c28fdaa1f034446e31e244c3012e9d6a0e1018feadac
4
+ data.tar.gz: 0a6b9cefe19dc6b61194037bfd2856f90dc74d09033b78a3edcbb508cbd92239
5
5
  SHA512:
6
- metadata.gz: 79844be2e538ec196567018344f52de6bb233ff0fe24d6a29ae19fe83c3f8dc6065a9cf1413a6c909ed0027a107c222d9eb531d516d256c3ac35b799efce9cc6
7
- data.tar.gz: 248e3a12c2a0500fff24054b09b89fce3fb84ed7851edebecc14c613f4bc36f513cdbfffdef09afe14fb229f3921ee8d839a5a3641c291a00a38c6b18dd1e4b9
6
+ metadata.gz: ceaa617e8d6f772d12dd08009b00df480098c268ff65dc03e5ee11da3a556353cd4ae507324497c8a1b1610810a9cc4ac811803c7c02b6d28749f3715a19fe45
7
+ data.tar.gz: 6bae554b970a8edb702b57fb18a401191fc7da6ff5acddaf21db76c1d6a4ab452a7f53e8c72178d7ed451a94ed72f155d2f7e5f5a4e6d0abdfb794eeab7e8cf1
@@ -0,0 +1,19 @@
1
+ module Admin
2
+ class CpdBulkAuditsController < ApplicationController
3
+ before_action(:authenticate_user!) if defined?(Devise)
4
+ before_action { EffectiveResources.authorize!(self, :admin, :effective_cpd) }
5
+
6
+ include Effective::CrudController
7
+
8
+ resource_scope -> { EffectiveCpd.CpdBulkAudit.deep.all }
9
+ datatable -> { EffectiveResources.best('Admin::EffectiveCpdBulkAuditsDatatable').new }
10
+
11
+ private
12
+
13
+ def permitted_params
14
+ model = (params.key?(:effective_cpd_bulk_audit) ? :effective_cpd_bulk_audit : :cpd_bulk_audit)
15
+ params.require(model).permit!
16
+ end
17
+
18
+ end
19
+ end
@@ -0,0 +1,24 @@
1
+ module Admin
2
+ class EffectiveCpdBulkAuditAuditReviewersDatatable < Effective::Datatable
3
+
4
+ datatable do
5
+ order :updated_at, :desc
6
+
7
+ col :id, visible: false
8
+ col :updated_at, label: 'Updated', visible: false
9
+ col :created_at, label: 'Created', visible: false
10
+
11
+ col :first_name
12
+ col :last_name
13
+ col :email
14
+
15
+ actions_col(only: [:show, :edit])
16
+
17
+ end
18
+
19
+ collection do
20
+ current_user.class.send(EffectiveCpd.audit_reviewer_user_scope)
21
+ end
22
+
23
+ end
24
+ end
@@ -0,0 +1,23 @@
1
+ module Admin
2
+ class EffectiveCpdBulkAuditAuditeesDatatable < Effective::Datatable
3
+
4
+ datatable do
5
+ order :updated_at, :desc
6
+
7
+ col :id, visible: false
8
+ col :updated_at, label: 'Updated', visible: false
9
+ col :created_at, label: 'Created', visible: false
10
+
11
+ col :first_name
12
+ col :last_name
13
+ col :email
14
+
15
+ actions_col(only: [:show, :edit])
16
+ end
17
+
18
+ collection do
19
+ current_user.class.send(EffectiveCpd.auditee_user_scope)
20
+ end
21
+
22
+ end
23
+ end
@@ -0,0 +1,25 @@
1
+ module Admin
2
+ class EffectiveCpdBulkAuditsDatatable < Effective::Datatable
3
+
4
+ datatable do
5
+ order :updated_at, :desc
6
+
7
+ col :id, visible: false
8
+ col :updated_at, label: 'Updated', visible: false
9
+ col :created_at, label: 'Created'
10
+
11
+ col :cpd_audit_level
12
+ col :audits
13
+ col :audit_reviewers_per_audit
14
+ col :notification_date
15
+ col :email_form_skip
16
+
17
+ actions_col
18
+ end
19
+
20
+ collection do
21
+ EffectiveCpd.CpdBulkAudit.all
22
+ end
23
+
24
+ end
25
+ end
@@ -0,0 +1,10 @@
1
+ module Effective
2
+ class CpdBulkAuditJob < ApplicationJob
3
+
4
+ def perform(id)
5
+ bulk_audit = EffectiveCpd.CpdBulkAudit.find(id)
6
+ bulk_audit.create_audits!
7
+ end
8
+
9
+ end
10
+ end
@@ -308,7 +308,7 @@ module EffectiveCpdAudit
308
308
  end
309
309
 
310
310
  def draft?
311
- !was_submitted?
311
+ !was_submitted? && !closed?
312
312
  end
313
313
 
314
314
  def in_progress?
@@ -0,0 +1,158 @@
1
+ # frozen_string_literal: true
2
+
3
+ # EffectiveCpdBulkAudit
4
+ #
5
+ # Mark your owner model with effective_cpd_bulk_audit to get all the includes
6
+
7
+ module EffectiveCpdBulkAudit
8
+ extend ActiveSupport::Concern
9
+
10
+ module Base
11
+ def effective_cpd_bulk_audit
12
+ include ::EffectiveCpdBulkAudit
13
+ end
14
+ end
15
+
16
+ module ClassMethods
17
+ def effective_cpd_bulk_audit?; true; end
18
+ end
19
+
20
+ included do
21
+ attr_accessor :current_user
22
+
23
+ # App scoped
24
+ belongs_to :cpd_audit_level, polymorphic: true
25
+
26
+ log_changes if respond_to?(:log_changes)
27
+
28
+ effective_resource do
29
+ cpd_user_class_name :string
30
+
31
+ audits :integer
32
+ audit_reviewers_per_audit :integer
33
+
34
+ notification_date :date
35
+ email_form_skip :boolean
36
+
37
+ auditees_count :integer
38
+ audit_reviewers_count :integer
39
+
40
+ timestamps
41
+ end
42
+
43
+ scope :deep, -> { includes(:cpd_audit_level) }
44
+ scope :sorted, -> { order(:id) }
45
+
46
+ before_validation(if: -> { current_user.present? }) do
47
+ self.cpd_user_class_name ||= current_user.class.name
48
+ end
49
+
50
+ before_validation do
51
+ self.notification_date ||= Time.zone.now
52
+ end
53
+
54
+ before_validation(if: -> { cpd_user_scope.present? }) do
55
+ self.auditees_count ||= cpd_auditees.count()
56
+ self.audit_reviewers_count ||= cpd_audit_reviewers.count()
57
+ end
58
+
59
+ validates :cpd_user_class_name, presence: true
60
+
61
+ validates :audits, presence: true, numericality: { greater_than: 0, less_than_or_equal_to: 1000 }
62
+ validates :audit_reviewers_per_audit, presence: true, numericality: { greater_than: 0, less_than_or_equal_to: 3 }
63
+
64
+ validates :auditees_count, numericality: { greater_than: 0 }
65
+ validates :audit_reviewers_count, numericality: { greater_than: 0 }
66
+
67
+ validate(if: -> { cpd_user_scope.present? }) do
68
+ self.errors.add(:cpd_user_class_name, "expecting an effective_cpd_user") unless cpd_user_scope.respond_to?(:effective_cpd_user?)
69
+ end
70
+
71
+ validate(if: -> { audits.present? && auditees_count.present? }) do
72
+ self.errors.add(:audits, "can't be more than the number of auditees #{auditees_count}") if audits > auditees_count
73
+ end
74
+
75
+ validate(if: -> { audit_reviewers_per_audit.present? && audit_reviewers_count.present? }) do
76
+ self.errors.add(:audit_reviewers_per_audit, "can't be more than the number of audit reviewers #{audit_reviewers_count}") if audit_reviewers_per_audit > audit_reviewers_count
77
+ end
78
+
79
+ after_commit(on: :create) { create_bulk_audit_job! }
80
+ end
81
+
82
+ def to_s
83
+ 'bulk audit'
84
+ end
85
+
86
+ def cpd_user_scope
87
+ cpd_user_class_name.constantize.all if cpd_user_class_name.present?
88
+ end
89
+
90
+ def cpd_auditees
91
+ cpd_user_scope.send(EffectiveCpd.auditee_user_scope)
92
+ end
93
+
94
+ def cpd_audit_reviewers
95
+ cpd_user_scope.send(EffectiveCpd.audit_reviewer_user_scope)
96
+ end
97
+
98
+ def create_bulk_audit_job!
99
+ raise('must be persisted') unless persisted?
100
+
101
+ Effective::CpdBulkAuditJob.perform_later(id)
102
+ end
103
+
104
+ # Called by Effective::CpdBulkAuditJob
105
+ def create_audits!
106
+ save!
107
+
108
+ @auditees = cpd_auditees.order('RANDOM()').limit(audits)
109
+ @reviewers = cpd_audit_reviewers.order('RANDOM()').limit(audits).to_a
110
+
111
+ @auditees.each do |auditee|
112
+ reviewers = audit_reviewers_per_audit.times.map { next_audit_reviewer() }
113
+
114
+ cpd_audit = build_cpd_audit(auditee, reviewers)
115
+ cpd_audit.save!
116
+ end
117
+
118
+ true
119
+ end
120
+
121
+ def build_cpd_audit(auditee, reviewers)
122
+ raise('expected auditee cpd user') unless auditee.class.respond_to?(:effective_cpd_user?)
123
+
124
+ reviewers = Array(reviewers)
125
+ raise('expected audit reviewers') unless reviewers.all? { |reviewer| reviewer.try(:cpd_audit_reviewer?) }
126
+
127
+ cpd_audit = EffectiveCpd.CpdAudit.new(
128
+ cpd_audit_level: cpd_audit_level,
129
+ email_form_skip: email_form_skip?,
130
+ user: auditee,
131
+ notification_date: notification_date
132
+ )
133
+
134
+ reviewers.each do |reviewer|
135
+ cpd_audit.cpd_audit_reviews.build(
136
+ cpd_audit_level: cpd_audit_level,
137
+ email_form_skip: email_form_skip?,
138
+ user: reviewer
139
+ )
140
+ end
141
+
142
+ cpd_audit
143
+ end
144
+
145
+ # Round robin
146
+ def next_audit_reviewer
147
+ raise('expected @audit_reviewers to be set') unless @reviewers
148
+
149
+ @reviewers_index ||= -1
150
+
151
+ # Next Reviewer
152
+ @reviewers_index += 1
153
+ @reviewers_index = 0 if @reviewers_index >= @reviewers.length
154
+
155
+ @reviewers[@reviewers_index]
156
+ end
157
+
158
+ end
@@ -24,7 +24,7 @@ module EffectiveCpdUser
24
24
  has_many :cpd_audits, -> { order(:id) }, inverse_of: :user
25
25
  has_many :cpd_audit_reviews, -> { order(:id) }, inverse_of: :user
26
26
 
27
- scope :cpd_audit_auditees, -> { without_role(:cpd_audit_reviewer) }
27
+ scope :cpd_audit_auditees, -> { without_role(:cpd_audit_reviewer).without_role(:admin) }
28
28
  scope :cpd_audit_reviewers, -> { with_role(:cpd_audit_reviewer) }
29
29
  end
30
30
 
@@ -0,0 +1,5 @@
1
+ module Effective
2
+ class CpdBulkAudit < ActiveRecord::Base
3
+ effective_cpd_bulk_audit
4
+ end
5
+ end
@@ -0,0 +1 @@
1
+ = render('admin/cpd_bulk_audits/form_cpd_bulk_audit', cpd_bulk_audit: cpd_bulk_audit)
@@ -0,0 +1,60 @@
1
+ %h2 Bulk Create Audits
2
+
3
+ = effective_form_with(model: [:admin, cpd_bulk_audit], engine: true, url: effective_cpd.admin_cpd_bulk_audits_path) do |f|
4
+ = f.number_field :audits, label: 'How many audits to create', placeholder: 100
5
+ = f.number_field :audit_reviewers_per_audit, label: 'How many reviewers should be assigned to each audit', placeholder: 1
6
+
7
+ = f.hidden_field :cpd_audit_level_type, value: EffectiveCpd.CpdAuditLevel.name
8
+ = f.select :cpd_audit_level_id, EffectiveCpd.CpdAuditLevel.new_cpd_audit_level_collection, label: 'Audit level'
9
+
10
+ = f.date_field :notification_date, label: 'Date of notification', required: false, placeholder: Time.zone.now.strftime('%F'),
11
+ hint: "the starting date for any deadline calculations. leave blank for today's date"
12
+
13
+ %h3 Eligible Auditees
14
+ - datatable = EffectiveResources.best('Admin::EffectiveCpdBulkAuditAuditeesDatatable').new(self)
15
+ - raise('expected an auditees datatable') unless datatable.present?
16
+
17
+ %p The following #{pluralize(datatable.collection.count, 'auditee')} may be selected for audit:
18
+ = collapse('Show auditees...', card_class: '') do
19
+ = render_datatable(datatable)
20
+
21
+ %h3 Eligible Audit Reviewers
22
+ - datatable = EffectiveResources.best('Admin::EffectiveCpdBulkAuditAuditReviewersDatatable').new(self)
23
+ - raise('expected an auditees datatable') unless datatable.present?
24
+
25
+ %p The following #{pluralize(datatable.collection.count, 'audit reviewer')} may be selected to review audits:
26
+ = collapse('Show audit reviewers...', card_class: '') do
27
+ = render_datatable(datatable)
28
+
29
+ %h3 Email to send
30
+ = f.check_box :email_form_skip, label: 'Do not send email'
31
+
32
+ = f.show_if :email_form_skip, true do
33
+ %p No emails will be sent.
34
+
35
+ = f.hide_if :email_form_skip, true do
36
+ %p
37
+ The
38
+ - email = Effective::EmailTemplate.where(template_name: :cpd_audit_opened).first!
39
+ = link_to('cpd_audit_opened email', effective_email_templates.edit_admin_email_template_path(email), target: '_blank')
40
+ email will be sent to each auditee.
41
+
42
+ %p
43
+ The
44
+ - email = Effective::EmailTemplate.where(template_name: :cpd_audit_review_opened).first!
45
+ = link_to('cpd_audit_review_opened email', effective_email_templates.edit_admin_email_template_path(email), target: '_blank')
46
+ email will be sent to each audit reviewer.
47
+
48
+ %h3 Create Audits
49
+
50
+ %p
51
+ Upon clicking the button below, the audits will be created in a background process.
52
+
53
+ %p
54
+ The auditees will be randomly selected, and the audit reviewers assigned in a round robin fashion.
55
+ This process will take a few minutes.
56
+
57
+ %p
58
+ All created audits will be displayed on the #{link_to 'Audits', effective_cpd.admin_cpd_audits_path} screen.
59
+
60
+ = f.submit 'Create Bulk Audits', center: true, 'data-confirm': "Really create audits?"
@@ -1,4 +1,5 @@
1
- = wizard_card(cpd_audit) do
1
+ - # don't use wizard_card here
2
+ = card(cpd_audit.wizard_step_title(step)) do
2
3
  %table.table
3
4
  %tbody
4
5
  %tr
@@ -1,4 +1,5 @@
1
- = wizard_card(cpd_audit) do
1
+ - # don't use wizard_card here
2
+ = card(cpd_audit.wizard_step_title(step)) do
2
3
  %table.table
3
4
  %tbody
4
5
  %tr
@@ -1,4 +1,5 @@
1
- = wizard_card(cpd_audit) do
1
+ - # don't use wizard_card here
2
+ = card(cpd_audit.wizard_step_title(step)) do
2
3
  %table.table
3
4
  %tbody
4
5
  %tr
@@ -22,6 +22,8 @@ EffectiveCpd.setup do |config|
22
22
  config.cpd_audit_reviews_table_name = :cpd_audit_reviews
23
23
  config.cpd_audit_review_items_table_name = :cpd_audit_review_items
24
24
 
25
+ config.cpd_bulk_audits_table_name = :cpd_bulk_audits
26
+
25
27
  # Layout Settings
26
28
  # Configure the Layout per controller, or all at once
27
29
  config.layout = {
@@ -35,6 +37,7 @@ EffectiveCpd.setup do |config|
35
37
  # config.cpd_audit_class_name = 'Effective::CpdAudit'
36
38
  # config.cpd_audit_level_class_name = 'Effective::CpdAuditLevel'
37
39
  # config.cpd_audit_review_class_name = 'Effective::CpdAuditReview'
40
+ # config.cpd_bulk_audit_class_name = 'Effective::CpdBulkAudit'
38
41
 
39
42
  # Program label settings
40
43
  config.program_label = 'CPD' # CPD or MCE
data/config/routes.rb CHANGED
@@ -46,6 +46,8 @@ EffectiveCpd::Engine.routes.draw do
46
46
 
47
47
  resources :cpd_audits, except: [:show]
48
48
  resources :cpd_audit_reviews
49
+
50
+ resources :cpd_bulk_audits, only: [:index, :new, :create]
49
51
  end
50
52
 
51
53
  end
@@ -305,5 +305,22 @@ class CreateEffectiveCpd < ActiveRecord::Migration[6.0]
305
305
  t.datetime :created_at
306
306
  end
307
307
 
308
+ create_table <%= @cpd_bulk_audits_table_name %> do |t|
309
+ t.integer :cpd_audit_level_id
310
+ t.string :cpd_audit_level_type
311
+
312
+ t.integer :audits
313
+ t.integer :audit_reviewers_per_audit
314
+
315
+ t.date :notification_date
316
+ t.boolean :email_form_skip
317
+
318
+ t.string :user_klass
319
+ t.integer :auditees_count
320
+ t.integer :audit_reviewers_count
321
+
322
+ t.timestamps
323
+ end
324
+
308
325
  end
309
326
  end
@@ -11,11 +11,11 @@ module EffectiveCpd
11
11
  initializer 'effective_cpd.active_record' do |app|
12
12
  ActiveSupport.on_load :active_record do
13
13
  ActiveRecord::Base.extend(EffectiveCpdUser::Base)
14
- #ActiveRecord::Base.extend(EffectiveCpdCycle::Base)
15
14
  ActiveRecord::Base.extend(EffectiveCpdStatement::Base)
16
15
  ActiveRecord::Base.extend(EffectiveCpdAudit::Base)
17
16
  ActiveRecord::Base.extend(EffectiveCpdAuditLevel::Base)
18
17
  ActiveRecord::Base.extend(EffectiveCpdAuditReview::Base)
18
+ ActiveRecord::Base.extend(EffectiveCpdBulkAudit::Base)
19
19
  end
20
20
  end
21
21
 
@@ -1,3 +1,3 @@
1
1
  module EffectiveCpd
2
- VERSION = '1.1.3'
2
+ VERSION = '1.2.1'
3
3
  end
data/lib/effective_cpd.rb CHANGED
@@ -13,11 +13,11 @@ module EffectiveCpd
13
13
  :cpd_audit_levels_table_name, :cpd_audit_level_sections_table_name,
14
14
  :cpd_audit_level_questions_table_name, :cpd_audit_level_question_options_table_name,
15
15
  :cpd_audits_table_name, :cpd_audit_responses_table_name, :cpd_audit_response_options_table_name,
16
- :cpd_audit_reviews_table_name, :cpd_audit_review_items_table_name,
16
+ :cpd_audit_reviews_table_name, :cpd_audit_review_items_table_name, :cpd_bulk_audits_table_name,
17
17
  :program_label, :cycle_label, :credit_label, :layout, :auditee_user_scope, :audit_reviewer_user_scope,
18
18
  :use_effective_messaging,
19
19
  :mailer, :parent_mailer, :deliver_method, :mailer_layout, :mailer_sender, :mailer_admin, :mailer_subject, :use_effective_email_templates,
20
- :cpd_statement_class_name, :cpd_audit_class_name, :cpd_audit_level_class_name, :cpd_audit_review_class_name
20
+ :cpd_statement_class_name, :cpd_audit_class_name, :cpd_audit_level_class_name, :cpd_audit_review_class_name, :cpd_bulk_audit_class_name
21
21
  ]
22
22
  end
23
23
 
@@ -43,6 +43,10 @@ module EffectiveCpd
43
43
  cpd_audit_review_class_name&.constantize || Effective::CpdAuditReview
44
44
  end
45
45
 
46
+ def self.CpdBulkAudit
47
+ cpd_bulk_audit_class_name&.constantize || Effective::CpdBulkAudit
48
+ end
49
+
46
50
  def self.use_effective_messaging?
47
51
  defined?(EffectiveMessaging) && !!use_effective_messaging
48
52
  end
@@ -43,6 +43,8 @@ module EffectiveCpd
43
43
  @cpd_audit_reviews_table_name = ':' + EffectiveCpd.cpd_audit_reviews_table_name.to_s
44
44
  @cpd_audit_review_items_table_name = ':' + EffectiveCpd.cpd_audit_review_items_table_name.to_s
45
45
 
46
+ @cpd_bulk_audits_table_name = ':' + EffectiveCpd.cpd_bulk_audits_table_name.to_s
47
+
46
48
  migration_template ('../' * 3) + 'db/migrate/01_create_effective_cpd.rb.erb', 'db/migrate/create_effective_cpd.rb'
47
49
  end
48
50
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: effective_cpd
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.3
4
+ version: 1.2.1
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-01-20 00:00:00.000000000 Z
11
+ date: 2023-01-23 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -150,6 +150,20 @@ dependencies:
150
150
  - - ">="
151
151
  - !ruby/object:Gem::Version
152
152
  version: '0'
153
+ - !ruby/object:Gem::Dependency
154
+ name: effective_developer
155
+ requirement: !ruby/object:Gem::Requirement
156
+ requirements:
157
+ - - ">="
158
+ - !ruby/object:Gem::Version
159
+ version: '0'
160
+ type: :development
161
+ prerelease: false
162
+ version_requirements: !ruby/object:Gem::Requirement
163
+ requirements:
164
+ - - ">="
165
+ - !ruby/object:Gem::Version
166
+ version: '0'
153
167
  - !ruby/object:Gem::Dependency
154
168
  name: effective_email_templates
155
169
  requirement: !ruby/object:Gem::Requirement
@@ -178,6 +192,20 @@ dependencies:
178
192
  - - ">="
179
193
  - !ruby/object:Gem::Version
180
194
  version: '0'
195
+ - !ruby/object:Gem::Dependency
196
+ name: effective_roles
197
+ requirement: !ruby/object:Gem::Requirement
198
+ requirements:
199
+ - - ">="
200
+ - !ruby/object:Gem::Version
201
+ version: '0'
202
+ type: :development
203
+ prerelease: false
204
+ version_requirements: !ruby/object:Gem::Requirement
205
+ requirements:
206
+ - - ">="
207
+ - !ruby/object:Gem::Version
208
+ version: '0'
181
209
  description: Continuing professional development and audits rails engine
182
210
  email:
183
211
  - info@codeandeffect.com
@@ -199,6 +227,7 @@ files:
199
227
  - app/controllers/admin/cpd_audit_levels_controller.rb
200
228
  - app/controllers/admin/cpd_audit_reviews_controller.rb
201
229
  - app/controllers/admin/cpd_audits_controller.rb
230
+ - app/controllers/admin/cpd_bulk_audits_controller.rb
202
231
  - app/controllers/admin/cpd_categories_controller.rb
203
232
  - app/controllers/admin/cpd_cycles_controller.rb
204
233
  - app/controllers/admin/cpd_rules_controller.rb
@@ -215,6 +244,9 @@ files:
215
244
  - app/datatables/admin/effective_cpd_audit_levels_datatable.rb
216
245
  - app/datatables/admin/effective_cpd_audit_reviews_datatable.rb
217
246
  - app/datatables/admin/effective_cpd_audits_datatable.rb
247
+ - app/datatables/admin/effective_cpd_bulk_audit_audit_reviewers_datatable.rb
248
+ - app/datatables/admin/effective_cpd_bulk_audit_auditees_datatable.rb
249
+ - app/datatables/admin/effective_cpd_bulk_audits_datatable.rb
218
250
  - app/datatables/admin/effective_cpd_categories_datatable.rb
219
251
  - app/datatables/admin/effective_cpd_cycles_datatable.rb
220
252
  - app/datatables/admin/effective_cpd_rules_datatable.rb
@@ -229,10 +261,12 @@ files:
229
261
  - app/datatables/effective_cpd_completed_statements_datatable.rb
230
262
  - app/helpers/effective_cpd_audits_helper.rb
231
263
  - app/helpers/effective_cpd_helper.rb
264
+ - app/jobs/effective/cpd_bulk_audit_job.rb
232
265
  - app/mailers/effective/cpd_mailer.rb
233
266
  - app/models/concerns/effective_cpd_audit.rb
234
267
  - app/models/concerns/effective_cpd_audit_level.rb
235
268
  - app/models/concerns/effective_cpd_audit_review.rb
269
+ - app/models/concerns/effective_cpd_bulk_audit.rb
236
270
  - app/models/concerns/effective_cpd_statement.rb
237
271
  - app/models/concerns/effective_cpd_user.rb
238
272
  - app/models/effective/cpd_activity.rb
@@ -245,6 +279,7 @@ files:
245
279
  - app/models/effective/cpd_audit_response_option.rb
246
280
  - app/models/effective/cpd_audit_review.rb
247
281
  - app/models/effective/cpd_audit_review_item.rb
282
+ - app/models/effective/cpd_bulk_audit.rb
248
283
  - app/models/effective/cpd_category.rb
249
284
  - app/models/effective/cpd_cycle.rb
250
285
  - app/models/effective/cpd_rule.rb
@@ -278,6 +313,8 @@ files:
278
313
  - app/views/admin/cpd_audits/_form_new.html.haml
279
314
  - app/views/admin/cpd_audits/_form_process.html.haml
280
315
  - app/views/admin/cpd_audits/_status.html.haml
316
+ - app/views/admin/cpd_bulk_audits/_form.html.haml
317
+ - app/views/admin/cpd_bulk_audits/_form_cpd_bulk_audit.html.haml
281
318
  - app/views/admin/cpd_categories/_form.html.haml
282
319
  - app/views/admin/cpd_categories/_form_cpd_category.html.haml
283
320
  - app/views/admin/cpd_cycles/_form.html.haml